From 72703f4e3d895263a0ed49976b3dccf8bbb49c74 Mon Sep 17 00:00:00 2001 From: bchoudhary6415 <95407446+bchoudhary6415@users.noreply.github.com> Date: Fri, 4 Oct 2024 16:16:35 +0530 Subject: [PATCH] Support for logging in ibm_db module (#964) Signed-off-by: Balram Choudhary --- README.md | 23 + ibm_db.c | 3778 +++++++++++++++++++++++++++++++++++++++++++----- ibmdb_tests.py | 3 + 3 files changed, 3470 insertions(+), 334 deletions(-) diff --git a/README.md b/README.md index 718bfb6b..cd57d4e6 100644 --- a/README.md +++ b/README.md @@ -275,6 +275,29 @@ True ## Logging +### Logging in ibm_db Module +You can enable logging in the ibm_db module to debug and trace activities. +Logging can be directed to the console or a specified file. + +To enable logging: +``` +import ibm_db + +# Log to console +ibm_db.debug(True) + +# Log to a file (e.g., log.txt) +ibm_db.debug("log.txt") + +# stop logging +ibm_db.debug(False) +``` +Calling ibm_db.debug(True) with boolean True argument will output logs to the console. + +Calling ibm_db.debug("log.txt") will log messages to the specified file (log.txt in this example). + +Calling ibm_db.debug(False) with boolean False argument will stop logging. + ### Logging in ibm_db_dbi Module You can enable logging in the ibm_db_dbi module to debug and trace activities. Logging can be directed to the console or a specified file. diff --git a/ibm_db.c b/ibm_db.c index 7ea63149..f585e147 100644 --- a/ibm_db.c +++ b/ibm_db.c @@ -90,6 +90,50 @@ static int is_systemi, is_informix; /* 1 == TRUE; 0 == FALSE; */ #define LIBDB2 "libdb2.so.1" #endif +// Define macros for log levels +#define DEBUG "DEBUG" +#define INFO "INFO" +#define WARNING "WARNING" +#define ERROR "ERROR" +#define EXCEPTION "EXCEPTION" + + +static int debug_mode = 0; +static char* fileName = NULL; +static char messageStr[2024]; + +// Function to get the current timestamp +static void get_timestamp(char *buffer, size_t size) { + time_t now = time(NULL); + struct tm *tm_info = localtime(&now); + strftime(buffer, size, "%Y-%m-%d %H:%M:%S", tm_info); +} + +// LogMsg function +static void LogMsg(const char *log_level, const char *message, const char *file_name) { + // logging if in debug mode + if (debug_mode) + { + char timestamp[20]; + get_timestamp(timestamp, sizeof(timestamp)); + + // Print formatted log message + if (file_name == NULL) { + printf("%s - %s - %s\n", timestamp, log_level, message); + } else { + FILE *file = fopen(file_name, "a"); + if (file != NULL) { + fprintf(file, "%s - %s - %s\n", timestamp, log_level, message); + fclose(file); + } else { + printf("Failed to open log file: %s\n", file_name); + } + } + } else { + return; + } +} + /* Defines a linked list structure for error messages */ typedef struct _error_msg_node { char err_msg[DB2_MAX_ERR_MSG_LEN]; @@ -337,20 +381,36 @@ char *strtoupper(char *data, int max) { /* static void _python_ibm_db_free_conn_struct */ static void _python_ibm_db_free_conn_struct(conn_handle *handle) { - + LogMsg(INFO, "entry _python_ibm_db_free_conn_struct", fileName); /* Disconnect from DB. If stmt is allocated, it is freed automatically */ + snprintf(messageStr, sizeof(messageStr), "Handle details: handle_active=%d, flag_pconnect=%d, auto_commit=%d", + handle->handle_active, handle->flag_pconnect, handle->auto_commit); + LogMsg(DEBUG, messageStr, fileName); if ( handle->handle_active && !handle->flag_pconnect) { if(handle->auto_commit == 0){ Py_BEGIN_ALLOW_THREADS; SQLEndTran(SQL_HANDLE_DBC, (SQLHDBC)handle->hdbc, SQL_ROLLBACK); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLEndTran called with SQL_HANDLE_DBC=%d, hdbc=%p, SQL_ROLLBACK=%d", + SQL_HANDLE_DBC, (void *)handle->hdbc, SQL_ROLLBACK); + LogMsg(DEBUG, messageStr, fileName); } Py_BEGIN_ALLOW_THREADS; SQLDisconnect((SQLHDBC)handle->hdbc); + snprintf(messageStr, sizeof(messageStr), "SQLDisconnect called with hdbc=%p", (void *)handle->hdbc); + LogMsg(DEBUG, messageStr, fileName); SQLFreeHandle(SQL_HANDLE_DBC, handle->hdbc); + snprintf(messageStr, sizeof(messageStr), "SQLFreeHandle called with SQL_HANDLE_DBC=%d, handle_hdbc=%p", SQL_HANDLE_DBC, (void *)handle->hdbc); + LogMsg(DEBUG, messageStr, fileName); SQLFreeHandle(SQL_HANDLE_ENV, handle->henv); + snprintf(messageStr, sizeof(messageStr), "SQLFreeHandle called with SQL_HANDLE_ENV=%d, handle->henv=%p", SQL_HANDLE_ENV, (void *)handle->henv); + LogMsg(DEBUG, messageStr, fileName); Py_END_ALLOW_THREADS; + } else { + snprintf(messageStr, sizeof(messageStr), "Connection not active or is a persistent connection. No disconnect needed."); + LogMsg(INFO, messageStr, fileName); } + LogMsg(INFO, "exit _python_ibm_db_free_conn_struct", fileName); Py_TYPE(handle)->tp_free((PyObject*)handle); } @@ -363,12 +423,21 @@ static void _python_ibm_db_free_conn_struct(conn_handle *handle) { static void _python_ibm_db_clear_param_cache( stmt_handle *stmt_res ) { + LogMsg(INFO, "entry _python_ibm_db_clear_param_cache()", fileName); + snprintf(messageStr, sizeof(messageStr), "Initial state: head_cache_list=%p, num_params=%d", + stmt_res->head_cache_list, stmt_res->num_params); + LogMsg(DEBUG, messageStr, fileName); param_node *temp_ptr, *curr_ptr; /* Free param cache list */ curr_ptr = stmt_res->head_cache_list; while (curr_ptr != NULL) { + snprintf(messageStr, sizeof(messageStr), "Freeing node: var_pyvalue=%p, varname=%p, svalue=%p, uvalue=%p, date_value=%p, time_value=%p, ts_value=%p, ivalueArray=%p, fvalueArray=%p, bind_indicator_array=%p", + curr_ptr->var_pyvalue, curr_ptr->varname, curr_ptr->svalue, curr_ptr->uvalue, + curr_ptr->date_value, curr_ptr->time_value, curr_ptr->ts_value, + curr_ptr->ivalueArray, curr_ptr->fvalueArray, curr_ptr->bind_indicator_array); + LogMsg(DEBUG, messageStr, fileName); /* Decrement refcount on Python handle */ /* NOTE: Py_XDECREF checks NULL value */ Py_XDECREF(curr_ptr->var_pyvalue); @@ -393,13 +462,20 @@ static void _python_ibm_db_clear_param_cache( stmt_handle *stmt_res ) stmt_res->head_cache_list = NULL; stmt_res->num_params = 0; + snprintf(messageStr, sizeof(messageStr), "Final state: head_cache_list=%p, num_params=%d", + stmt_res->head_cache_list, stmt_res->num_params); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit _python_ibm_db_clear_param_cache()", fileName); } /* static void _python_ibm_db_free_result_struct(stmt_handle* handle) */ static void _python_ibm_db_free_result_struct(stmt_handle* handle) { + LogMsg(INFO, "entry _python_ibm_db_free_result_struct()", fileName); int i; if ( handle != NULL ) { + snprintf(messageStr, sizeof(messageStr), "handle=%p, num_columns=%d", (void *)handle, handle->num_columns); + LogMsg(DEBUG, messageStr, fileName); _python_ibm_db_clear_param_cache(handle); /* free row data cache */ @@ -420,28 +496,38 @@ static void _python_ibm_db_free_result_struct(stmt_handle* handle) { case SQL_XML: case SQL_DECFLOAT: if ( handle->row_data[i].data.str_val != NULL ) { + snprintf(messageStr, sizeof(messageStr), "Freeing row_data[%d].data.str_val=%p", i, handle->row_data[i].data.str_val); + LogMsg(DEBUG, messageStr, fileName); PyMem_Del(handle->row_data[i].data.str_val); handle->row_data[i].data.str_val = NULL; } if ( handle->row_data[i].data.w_val != NULL ) { + snprintf(messageStr, sizeof(messageStr), "Freeing row_data[%d].data.w_val=%p", i, handle->row_data[i].data.w_val); + LogMsg(DEBUG, messageStr, fileName); PyMem_Del(handle->row_data[i].data.w_val); handle->row_data[i].data.w_val = NULL; } break; case SQL_TYPE_TIMESTAMP: if ( handle->row_data[i].data.ts_val != NULL ) { + snprintf(messageStr, sizeof(messageStr), "Freeing row_data[%d].data.ts_val=%p", i, handle->row_data[i].data.ts_val); + LogMsg(DEBUG, messageStr, fileName); PyMem_Del(handle->row_data[i].data.ts_val); handle->row_data[i].data.ts_val = NULL; } break; case SQL_TYPE_DATE: if ( handle->row_data[i].data.date_val != NULL ) { + snprintf(messageStr, sizeof(messageStr), "Freeing row_data[%d].data.date_val=%p", i, handle->row_data[i].data.date_val); + LogMsg(DEBUG, messageStr, fileName); PyMem_Del(handle->row_data[i].data.date_val); handle->row_data[i].data.date_val = NULL; } break; case SQL_TYPE_TIME: if ( handle->row_data[i].data.time_val != NULL ) { + snprintf(messageStr, sizeof(messageStr), "Freeing row_data[%d].data.time_val=%p", i, handle->row_data[i].data.time_val); + LogMsg(DEBUG, messageStr, fileName); PyMem_Del(handle->row_data[i].data.time_val); handle->row_data[i].data.time_val = NULL; } @@ -455,9 +541,13 @@ static void _python_ibm_db_free_result_struct(stmt_handle* handle) { /* free column info cache */ if ( handle->column_info ) { for (i = 0; inum_columns; i++) { + snprintf(messageStr, sizeof(messageStr), "Freeing column_info[%d].name=%p", i, handle->column_info[i].name); + LogMsg(DEBUG, messageStr, fileName); PyMem_Del(handle->column_info[i].name); /* Mem free */ if(handle->column_info[i].mem_alloc){ + snprintf(messageStr, sizeof(messageStr), "Freeing column_info[%d].mem_alloc=%p", i, handle->column_info[i].mem_alloc); + LogMsg(DEBUG, messageStr, fileName); PyMem_Del(handle->column_info[i].mem_alloc); } } @@ -466,10 +556,15 @@ static void _python_ibm_db_free_result_struct(stmt_handle* handle) { handle->num_columns = 0; } } + LogMsg(INFO, "exit _python_ibm_db_free_result_struct()", fileName); } /* static stmt_handle *_ibm_db_new_stmt_struct(conn_handle* conn_res) */ static stmt_handle *_ibm_db_new_stmt_struct(conn_handle* conn_res) { + LogMsg(INFO, "entry _ibm_db_new_stmt_struct()", fileName); + snprintf(messageStr, sizeof(messageStr), "Initializing stmt_handle: hdbc=%p, c_bin_mode=%d, c_cursor_type=%d, c_case_mode=%d, c_use_wchar=%d", + conn_res->hdbc, conn_res->c_bin_mode, conn_res->c_cursor_type, conn_res->c_case_mode, conn_res->c_use_wchar); + LogMsg(DEBUG, messageStr, fileName); stmt_handle *stmt_res; stmt_res = PyObject_NEW(stmt_handle, &stmt_handleType); @@ -481,7 +576,9 @@ static stmt_handle *_ibm_db_new_stmt_struct(conn_handle* conn_res) { stmt_res->cursor_type = conn_res->c_cursor_type; stmt_res->s_case_mode = conn_res->c_case_mode; stmt_res->s_use_wchar = conn_res->c_use_wchar; - + snprintf(messageStr, sizeof(messageStr), "New stmt_handle initialized: hdbc=%p, s_bin_mode=%d, cursor_type=%d, s_case_mode=%d, s_use_wchar=%d", + stmt_res->hdbc, stmt_res->s_bin_mode, stmt_res->cursor_type, stmt_res->s_case_mode, stmt_res->s_use_wchar); + LogMsg(DEBUG, messageStr, fileName); stmt_res->head_cache_list = NULL; stmt_res->current_node = NULL; @@ -495,33 +592,53 @@ static stmt_handle *_ibm_db_new_stmt_struct(conn_handle* conn_res) { stmt_res->errormsg_recno_tracker = 1; stmt_res->row_data = NULL; - + snprintf(messageStr, sizeof(messageStr), "Final stmt_handle state: head_cache_list=%p, current_node=%p, num_params=%d, file_param=%d, column_info=%p, num_columns=%d, error_recno_tracker=%d, errormsg_recno_tracker=%d, row_data=%p", + stmt_res->head_cache_list, stmt_res->current_node, stmt_res->num_params, stmt_res->file_param, stmt_res->column_info, stmt_res->num_columns, stmt_res->error_recno_tracker, stmt_res->errormsg_recno_tracker, stmt_res->row_data); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit _ibm_db_new_stmt_struct()", fileName); return stmt_res; } /* static _python_ibm_db_free_stmt_struct */ static void _python_ibm_db_free_stmt_struct(stmt_handle *handle) { + LogMsg(INFO, "entry _python_ibm_db_free_stmt_struct()", fileName); if ( handle->hstmt != -1 ) { + snprintf(messageStr, sizeof(messageStr), "handle->hstmt=%p, preparing to call SQLFreeHandle", (void *)handle->hstmt); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; SQLFreeHandle( SQL_HANDLE_STMT, handle->hstmt); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLFreeHandle called with handle=%p", (void *)handle->hstmt); + LogMsg(DEBUG, messageStr, fileName); if ( handle ) { _python_ibm_db_free_result_struct(handle); } } + snprintf(messageStr, sizeof(messageStr), "Py_TYPE(handle)->tp_free called for handle=%p", (void *)handle); + LogMsg(DEBUG, messageStr, fileName); Py_TYPE(handle)->tp_free((PyObject*)handle); + LogMsg(INFO, "exit _python_ibm_db_free_stmt_struct()", fileName); } /* static void _python_ibm_db_init_error_info(stmt_handle *stmt_res) */ static void _python_ibm_db_init_error_info(stmt_handle *stmt_res) { + LogMsg(INFO, "entry _python_ibm_db_init_error_info()", fileName); + snprintf(messageStr, sizeof(messageStr), "Initial state: error_recno_tracker = %d, errormsg_recno_tracker = %d", + stmt_res->error_recno_tracker, stmt_res->errormsg_recno_tracker); + LogMsg(DEBUG, messageStr, fileName); stmt_res->error_recno_tracker = 1; stmt_res->errormsg_recno_tracker = 1; + snprintf(messageStr, sizeof(messageStr), "Modified state: error_recno_tracker = %d, errormsg_recno_tracker = %d", + stmt_res->error_recno_tracker, stmt_res->errormsg_recno_tracker); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit _python_ibm_db_init_error_info()", fileName); } /* static void _python_ibm_db_check_sql_errors( SQLHANDLE handle, SQLSMALLINT hType, int rc, int cpy_to_global, char* ret_str, int API SQLSMALLINT recno) */ static void _python_ibm_db_check_sql_errors( SQLHANDLE handle, SQLSMALLINT hType, int rc, int cpy_to_global, char* ret_str, int API, SQLSMALLINT recno ) { + LogMsg(INFO, "entry _python_ibm_db_check_sql_errors", fileName); SQLCHAR msg[SQL_MAX_MESSAGE_LENGTH + 1] = {0}; SQLCHAR sqlstate[SQL_SQLSTATE_SIZE + 1] = {0}; SQLCHAR errMsg[DB2_MAX_ERR_MSG_LEN] = {0}; @@ -531,10 +648,18 @@ static void _python_ibm_db_check_sql_errors( SQLHANDLE handle, SQLSMALLINT hType SQLINTEGER rc1 = SQL_SUCCESS; int i = 0; + snprintf(messageStr, sizeof(messageStr), "handle=%p, hType=%d, rc=%d, cpy_to_global=%d, API=%d, recno=%d", + handle, hType, rc, cpy_to_global, API, recno); + LogMsg(DEBUG, messageStr, fileName); + memset(errMsg, '\0', DB2_MAX_ERR_MSG_LEN); memset(msg, '\0', SQL_MAX_MESSAGE_LENGTH + 1); rc1 = SQLGetDiagRec( hType, handle, recno, sqlstate, &sqlcode, msg, SQL_MAX_MESSAGE_LENGTH + 1, &length ); + snprintf(messageStr, sizeof(messageStr), "SQLGetDiagRec returned rc1=%d, sqlstate=%s, sqlcode=%d, msg=%s, length=%d", + rc1, sqlstate, sqlcode, msg, length); + LogMsg(DEBUG, messageStr, fileName); + if ( rc1 == SQL_SUCCESS ) { while ((p = strchr( (char *)msg, '\n' ))) { @@ -550,6 +675,8 @@ static void _python_ibm_db_check_sql_errors( SQLHANDLE handle, SQLSMALLINT hType } } #endif + + LogMsg(ERROR, errMsg, fileName); if (cpy_to_global != 0 && rc != 1 ) { PyErr_SetString(PyExc_Exception, (char *) errMsg); } @@ -561,6 +688,10 @@ static void _python_ibm_db_check_sql_errors( SQLHANDLE handle, SQLSMALLINT hType if ( cpy_to_global ) { switch (hType) { case SQL_HANDLE_DBC: + snprintf(messageStr, sizeof(messageStr), + "Copying to global: SQL_HANDLE_DBC, sqlstate=%s, errMsg=%s", + sqlstate, errMsg); + LogMsg(DEBUG, messageStr, fileName); strncpy( IBM_DB_G(__python_conn_err_state), (char*)sqlstate, SQL_SQLSTATE_SIZE+1); strncpy( IBM_DB_G(__python_conn_err_msg), @@ -568,6 +699,10 @@ static void _python_ibm_db_check_sql_errors( SQLHANDLE handle, SQLSMALLINT hType break; case SQL_HANDLE_STMT: + snprintf(messageStr, sizeof(messageStr), + "Copying to global: SQL_HANDLE_STMT, sqlstate=%s, errMsg=%s", + sqlstate, errMsg); + LogMsg(DEBUG, messageStr, fileName); strncpy( IBM_DB_G(__python_stmt_err_state), (char*)sqlstate, SQL_SQLSTATE_SIZE+1); strncpy( IBM_DB_G(__python_stmt_err_msg), @@ -580,11 +715,15 @@ static void _python_ibm_db_check_sql_errors( SQLHANDLE handle, SQLSMALLINT hType switch (API) { case DB2_ERR: if ( ret_str != NULL ) { + snprintf(messageStr, sizeof(messageStr), "Returning SQLSTATE for DB2_ERR: %s", sqlstate); + LogMsg(DEBUG, messageStr, fileName); strncpy(ret_str, (char*)sqlstate, SQL_SQLSTATE_SIZE+1); } return; case DB2_ERRMSG: if ( ret_str != NULL ) { + snprintf(messageStr, sizeof(messageStr), "Returning error message for DB2_ERRMSG: %s", errMsg); + LogMsg(DEBUG, messageStr, fileName); strncpy(ret_str, (char*)errMsg, DB2_MAX_ERR_MSG_LEN); } return; @@ -598,6 +737,10 @@ static void _python_ibm_db_check_sql_errors( SQLHANDLE handle, SQLSMALLINT hType if ( cpy_to_global ) { switch ( hType ) { case SQL_HANDLE_DBC: + snprintf(messageStr, sizeof(messageStr), + "Copying warning to global: SQL_HANDLE_DBC, sqlstate=%s, errMsg=%s", + sqlstate, errMsg); + LogMsg(DEBUG, messageStr, fileName); strncpy(IBM_DB_G(__python_conn_warn_state), (char*)sqlstate, SQL_SQLSTATE_SIZE+1); strncpy(IBM_DB_G(__python_conn_warn_msg), @@ -605,6 +748,10 @@ static void _python_ibm_db_check_sql_errors( SQLHANDLE handle, SQLSMALLINT hType break; case SQL_HANDLE_STMT: + snprintf(messageStr, sizeof(messageStr), + "Copying warning to global: SQL_HANDLE_STMT, sqlstate=%s, errMsg=%s", + sqlstate, errMsg); + LogMsg(DEBUG, messageStr, fileName); strncpy(IBM_DB_G(__python_stmt_warn_state), (char*)sqlstate, SQL_SQLSTATE_SIZE+1); strncpy(IBM_DB_G(__python_stmt_warn_msg), @@ -615,6 +762,8 @@ static void _python_ibm_db_check_sql_errors( SQLHANDLE handle, SQLSMALLINT hType /* This call was made from ibm_db_errmsg or ibm_db_error or ibm_db_warn */ /* Check for error and return */ if ( (API == DB2_WARNMSG) && (ret_str != NULL) ) { + snprintf(messageStr, sizeof(messageStr), "Returning warning message for DB2_WARNMSG: %s", errMsg); + LogMsg(DEBUG, messageStr, fileName); strncpy(ret_str, (char*)errMsg, DB2_MAX_ERR_MSG_LEN); } return; @@ -627,6 +776,7 @@ static void _python_ibm_db_check_sql_errors( SQLHANDLE handle, SQLSMALLINT hType /* static int _python_ibm_db_assign_options( void *handle, int type, long opt_key, PyObject *data ) */ static int _python_ibm_db_assign_options( void *handle, int type, long opt_key, PyObject *data ) { + LogMsg(INFO, "entry _python_ibm_db_assign_options()", fileName); int rc = 0; long option_num = 0; SQLINTEGER value_int = 0; @@ -636,22 +786,32 @@ static int _python_ibm_db_assign_options( void *handle, int type, long opt_key, SQLWCHAR *option_str = NULL; #endif int isNewBuffer; - + snprintf(messageStr, sizeof(messageStr), "Parameters - Handle: %p, type: %d, opt_key: %ld, data: %p", handle, type, opt_key, data); + LogMsg(DEBUG, messageStr, fileName); /* First check to see if it is a non-cli attribut */ if (opt_key == ATTR_CASE) { option_num = NUM2LONG(data); + snprintf(messageStr, sizeof(messageStr), "ATTR_CASE option_num: %ld", option_num); + LogMsg(DEBUG, messageStr, fileName); if (type == SQL_HANDLE_STMT) { switch (option_num) { case CASE_LOWER: ((stmt_handle*)handle)->s_case_mode = CASE_LOWER; + snprintf(messageStr, sizeof(messageStr), "Setting s_case_mode to CASE_LOWER"); + LogMsg(DEBUG, messageStr, fileName); break; case CASE_UPPER: ((stmt_handle*)handle)->s_case_mode = CASE_UPPER; + snprintf(messageStr, sizeof(messageStr), "Setting s_case_mode to CASE_UPPER"); + LogMsg(DEBUG, messageStr, fileName); break; case CASE_NATURAL: ((stmt_handle*)handle)->s_case_mode = CASE_NATURAL; + snprintf(messageStr, sizeof(messageStr), "Setting s_case_mode to CASE_UPPER"); + LogMsg(DEBUG, messageStr, fileName); break; default: + LogMsg(EXCEPTION, "ATTR_CASE attribute must be one of CASE_LOWER, CASE_UPPER, or CASE_NATURAL", fileName); PyErr_SetString(PyExc_Exception, "ATTR_CASE attribute must be one of CASE_LOWER, CASE_UPPER, or CASE_NATURAL"); return -1; } @@ -659,32 +819,47 @@ static int _python_ibm_db_assign_options( void *handle, int type, long opt_key, switch (option_num) { case CASE_LOWER: ((conn_handle*)handle)->c_case_mode = CASE_LOWER; + snprintf(messageStr, sizeof(messageStr), "Setting c_case_mode to CASE_LOWER"); + LogMsg(DEBUG, messageStr, fileName); break; case CASE_UPPER: ((conn_handle*)handle)->c_case_mode = CASE_UPPER; + snprintf(messageStr, sizeof(messageStr), "Setting c_case_mode to CASE_UPPER"); + LogMsg(DEBUG, messageStr, fileName); break; case CASE_NATURAL: ((conn_handle*)handle)->c_case_mode = CASE_NATURAL; + snprintf(messageStr, sizeof(messageStr), "Setting c_case_mode to CASE_NATURAL"); + LogMsg(DEBUG, messageStr, fileName); break; default: + LogMsg(EXCEPTION, "ATTR_CASE attribute must be one of CASE_LOWER, CASE_UPPER, or CASE_NATURAL", fileName); PyErr_SetString(PyExc_Exception, "ATTR_CASE attribute must be one of CASE_LOWER, CASE_UPPER, or CASE_NATURAL"); return -1; } } else { + LogMsg(ERROR, "Connection or statement handle must be passed in.", fileName); PyErr_SetString(PyExc_Exception, "Connection or statement handle must be passed in."); return -1; } } else if (opt_key == USE_WCHAR) { option_num = NUM2LONG(data); + snprintf(messageStr, sizeof(messageStr), "USE_WCHAR option_num: %ld", option_num); + LogMsg(DEBUG, messageStr, fileName); if (type == SQL_HANDLE_STMT) { switch (option_num) { case WCHAR_YES: ((stmt_handle*)handle)->s_use_wchar = WCHAR_YES; + snprintf(messageStr, sizeof(messageStr), "Setting s_use_wchar to WCHAR_YES"); + LogMsg(DEBUG, messageStr, fileName); break; case WCHAR_NO: ((stmt_handle*)handle)->s_use_wchar = WCHAR_NO; + snprintf(messageStr, sizeof(messageStr), "Setting s_use_wchar to WCHAR_NO"); + LogMsg(DEBUG, messageStr, fileName); break; default: + LogMsg(EXCEPTION, "USE_WCHAR attribute must be one of WCHAR_YES or WCHAR_NO", fileName); PyErr_SetString(PyExc_Exception, "USE_WCHAR attribute must be one of WCHAR_YES or WCHAR_NO"); return -1; } @@ -693,11 +868,16 @@ static int _python_ibm_db_assign_options( void *handle, int type, long opt_key, switch (option_num) { case WCHAR_YES: ((conn_handle*)handle)->c_use_wchar = WCHAR_YES; + snprintf(messageStr, sizeof(messageStr), "Setting c_use_wchar to WCHAR_YES"); + LogMsg(DEBUG, messageStr, fileName); break; case WCHAR_NO: ((conn_handle*)handle)->c_use_wchar = WCHAR_NO; + snprintf(messageStr, sizeof(messageStr), "Setting c_use_wchar to WCHAR_NO"); + LogMsg(DEBUG, messageStr, fileName); break; default: + LogMsg(EXCEPTION, "USE_WCHAR attribute must be one of WCHAR_YES or WCHAR_NO", fileName); PyErr_SetString(PyExc_Exception, "USE_WCHAR attribute must be one of WCHAR_YES or WCHAR_NO"); return -1; } @@ -705,16 +885,28 @@ static int _python_ibm_db_assign_options( void *handle, int type, long opt_key, } else if (type == SQL_HANDLE_STMT) { if (PyString_Check(data)|| PyUnicode_Check(data)) { data = PyUnicode_FromObject(data); + snprintf(messageStr, sizeof(messageStr), "Converted data to Unicode: %p", data); + LogMsg(DEBUG, messageStr, fileName); #ifdef __MVS__ option_str = getUnicodeDataAsSQLCHAR(data, &isNewBuffer); + snprintf(messageStr, sizeof(messageStr), "Option string (SQLCHAR) pointer: %p, isNewBuffer: %d", option_str, isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLSetStmtAttr((SQLHSTMT)((stmt_handle *)handle)->hstmt, opt_key, (SQLPOINTER)option_str, SQL_IS_INTEGER ); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLSetStmtAttr called with hstmt: %p, opt_key: %ld, option_str: %p, SQL_IS_INTEGER, and returned rc: %d", + ((stmt_handle*)handle)->hstmt, opt_key, option_str, rc); + LogMsg(DEBUG, messageStr, fileName); #else option_str = getUnicodeDataAsSQLWCHAR(data, &isNewBuffer); + snprintf(messageStr, sizeof(messageStr), "Option string (SQLWCHAR) pointer: %p, isNewBuffer: %d", option_str, isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLSetStmtAttrW((SQLHSTMT)((stmt_handle *)handle)->hstmt, opt_key, (SQLPOINTER)option_str, SQL_IS_INTEGER ); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLSetStmtAttrW called with hstmt: %p, opt_key: %ld, option_str: %p, SQL_IS_INTEGER, and returned rc: %d", + ((stmt_handle*)handle)->hstmt, opt_key, option_str, rc); + LogMsg(DEBUG, messageStr, fileName); #endif if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)((stmt_handle *)handle)->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); @@ -724,20 +916,38 @@ static int _python_ibm_db_assign_options( void *handle, int type, long opt_key, } else { option_num = NUM2LONG(data); - if (opt_key == SQL_ATTR_AUTOCOMMIT && option_num == SQL_AUTOCOMMIT_OFF) ((conn_handle*)handle)->auto_commit = 0; - else if (opt_key == SQL_ATTR_AUTOCOMMIT && option_num == SQL_AUTOCOMMIT_ON) ((conn_handle*)handle)->auto_commit = 1; + snprintf(messageStr, sizeof(messageStr), "Option number: %ld", option_num); + LogMsg(DEBUG, messageStr, fileName); + if (opt_key == SQL_ATTR_AUTOCOMMIT && option_num == SQL_AUTOCOMMIT_OFF) { + ((conn_handle*)handle)->auto_commit = 0; + snprintf(messageStr, sizeof(messageStr), "Setting auto_commit to OFF"); + LogMsg(DEBUG, messageStr, fileName); + } + else if (opt_key == SQL_ATTR_AUTOCOMMIT && option_num == SQL_AUTOCOMMIT_ON) { + ((conn_handle*)handle)->auto_commit = 1; + snprintf(messageStr, sizeof(messageStr), "Setting auto_commit to ON"); + LogMsg(DEBUG, messageStr, fileName); + } Py_BEGIN_ALLOW_THREADS; rc = SQLSetStmtAttr((SQLHSTMT)((stmt_handle *)handle)->hstmt, opt_key, (SQLPOINTER)option_num, SQL_IS_INTEGER ); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLSetStmtAttr called with hstmt: %p, opt_key: %ld, option_num: %ld, SQL_IS_INTEGER, and returned rc: %d", + ((stmt_handle*)handle)->hstmt, opt_key, option_num, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)((stmt_handle *)handle)->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } if (opt_key == SQL_ATTR_CURSOR_TYPE){ ((stmt_handle *)handle)->cursor_type = option_num; + snprintf(messageStr, sizeof(messageStr), "Cursor type set to %ld", option_num); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_SUCCESS_WITH_INFO ) { Py_BEGIN_ALLOW_THREADS; rc = SQLGetStmtAttr( ((stmt_handle *)handle)->hstmt, opt_key, &value_int, SQL_IS_INTEGER, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetStmtAttr called with hstmt: %p, opt_key: %ld, value_int: %d, SQL_IS_INTEGER, and retured rc: %d", + ((stmt_handle*)handle)->hstmt, opt_key, value_int, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(((stmt_handle *)handle)->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); PyErr_Clear(); @@ -750,15 +960,27 @@ static int _python_ibm_db_assign_options( void *handle, int type, long opt_key, } else if (type == SQL_HANDLE_DBC) { if (PyString_Check(data)|| PyUnicode_Check(data)) { data = PyUnicode_FromObject(data); + snprintf(messageStr, sizeof(messageStr), "Converted data to Unicode: %p", data); + LogMsg(DEBUG, messageStr, fileName); #ifdef __MVS__ option_str = getUnicodeDataAsSQLCHAR(data, &isNewBuffer); + snprintf(messageStr, sizeof(messageStr), "Option string (SQLCHAR) pointer: %p, isNewBuffer: %d", option_str, isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLSetConnectAttr((SQLHSTMT)((conn_handle*)handle)->hdbc, opt_key, (SQLPOINTER)option_str, SQL_NTS); + snprintf(messageStr, sizeof(messageStr),"SQLSetConnectAttr called with hdbc: %p, opt_key: %ld, option_str: %p, SQL_NTS, and retured rc: %d", + ((conn_handle*)handle)->hdbc, opt_key, (void*)option_str, rc); + LogMsg(DEBUG, messageStr, fileName); Py_END_ALLOW_THREADS; #else option_str = getUnicodeDataAsSQLWCHAR(data, &isNewBuffer); + snprintf(messageStr, sizeof(messageStr), "Option string (SQLWCHAR) pointer: %p, isNewBuffer: %d", option_str, isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLSetConnectAttrW((SQLHSTMT)((conn_handle*)handle)->hdbc, opt_key, (SQLPOINTER)option_str, SQL_NTS); + snprintf(messageStr, sizeof(messageStr), "SQLSetConnectAttrW called with hdbc: %p, opt_key: %ld, option_str: %p, SQL_NTS, and retured rc: %d", + ((conn_handle*)handle)->hdbc, opt_key, (void*)option_str, rc); + LogMsg(INFO, messageStr, fileName); Py_END_ALLOW_THREADS; #endif if ( rc == SQL_ERROR ) { @@ -769,15 +991,31 @@ static int _python_ibm_db_assign_options( void *handle, int type, long opt_key, } else { option_num = NUM2LONG(data); - if (opt_key == SQL_ATTR_AUTOCOMMIT && option_num == SQL_AUTOCOMMIT_OFF) ((conn_handle*)handle)->auto_commit = 0; - else if (opt_key == SQL_ATTR_AUTOCOMMIT && option_num == SQL_AUTOCOMMIT_ON) ((conn_handle*)handle)->auto_commit = 1; + snprintf(messageStr, sizeof(messageStr), "Option number: %ld", option_num); + LogMsg(DEBUG, messageStr, fileName); + if (opt_key == SQL_ATTR_AUTOCOMMIT && option_num == SQL_AUTOCOMMIT_OFF) { + ((conn_handle*)handle)->auto_commit = 0; + snprintf(messageStr, sizeof(messageStr), "Setting auto_commit to OFF"); + LogMsg(DEBUG, messageStr, fileName); + } + else if (opt_key == SQL_ATTR_AUTOCOMMIT && option_num == SQL_AUTOCOMMIT_ON) { + ((conn_handle*)handle)->auto_commit = 1; + snprintf(messageStr, sizeof(messageStr), "Setting auto_commit to ON"); + LogMsg(DEBUG, messageStr, fileName); + } #ifdef __MVS__ Py_BEGIN_ALLOW_THREADS; rc = SQLSetConnectAttr((SQLHSTMT)((conn_handle*)handle)->hdbc, opt_key, (SQLPOINTER)option_num, SQL_IS_INTEGER); + snprintf(messageStr, sizeof(messageStr), "SQLSetConnectAttr called with hdbc: %p, opt_key: %ld, option_num: %ld, SQL_IS_INTEGER, and retured rc: %d", + ((conn_handle*)handle)->hdbc, opt_key, (long)option_num, rc); + LogMsg(DEBUG, messageStr, fileName); Py_END_ALLOW_THREADS; #else Py_BEGIN_ALLOW_THREADS; rc = SQLSetConnectAttrW((SQLHSTMT)((conn_handle*)handle)->hdbc, opt_key, (SQLPOINTER)option_num, SQL_IS_INTEGER); + snprintf(messageStr, sizeof(messageStr), "SQLSetConnectAttrW called with hdbc: %p, opt_key: %ld, option_num: %ld, SQL_IS_INTEGER, and retured rc: %d", + ((conn_handle*)handle)->hdbc, opt_key, (long)option_num, rc); + LogMsg(DEBUG, messageStr, fileName); Py_END_ALLOW_THREADS; #endif if ( rc == SQL_ERROR ) { @@ -785,9 +1023,11 @@ static int _python_ibm_db_assign_options( void *handle, int type, long opt_key, } } } else { + LogMsg(ERROR, "Connection or statement handle must be passed in.", fileName); PyErr_SetString(PyExc_Exception, "Connection or statement handle must be passed in."); return -1; } + LogMsg(INFO, "exit _python_ibm_db_assign_options()", fileName); return 0; } @@ -795,37 +1035,54 @@ static int _python_ibm_db_assign_options( void *handle, int type, long opt_key, */ static int _python_ibm_db_parse_options ( PyObject *options, int type, void *handle ) { + LogMsg(INFO, "entry _python_ibm_db_parse_options()", fileName); int numOpts = 0, i = 0; PyObject *keys = NULL; PyObject *key = NULL; /* Holds the Option Index Key */ PyObject *data = NULL; PyObject *tc_pass = NULL; int rc = 0; - + snprintf(messageStr, sizeof(messageStr), "Options parameter: %p, Type: %d, Handle: %p", options, type, handle); + LogMsg(INFO, messageStr, fileName); if ( !NIL_P(options) ) { keys = PyDict_Keys(options); numOpts = PyList_Size(keys); - + snprintf(messageStr, sizeof(messageStr), "Number of options: %d", numOpts); + LogMsg(INFO, messageStr, fileName); for ( i = 0; i < numOpts; i++) { key = PyList_GetItem(keys, i); data = PyDict_GetItem(options, key); - + snprintf(messageStr, sizeof(messageStr), "Option %d: Key: %ld, Data: %p", i, NUM2LONG(key), data); + LogMsg(INFO, messageStr, fileName); if(NUM2LONG(key) == SQL_ATTR_TRUSTED_CONTEXT_PASSWORD) { tc_pass = data; } else { + snprintf(messageStr, sizeof(messageStr), "Assigning option: Key: %ld, Data: %p", NUM2LONG(key), data); + LogMsg(INFO, messageStr, fileName); /* Assign options to handle. */ /* Sets the options in the handle with CLI/ODBC calls */ rc = _python_ibm_db_assign_options(handle, type, NUM2LONG(key), data); + snprintf(messageStr, sizeof(messageStr), "_python_ibm_db_assign_options returned: %d", rc); + LogMsg(INFO, messageStr, fileName); } - if (rc) + if (rc) { + LogMsg(INFO, "exit _python_ibm_db_parse_options()", fileName); return SQL_ERROR; + } } if (!NIL_P(tc_pass) ) { + snprintf(messageStr, sizeof(messageStr), "Assigning trusted context password: %p", tc_pass); + LogMsg(INFO, messageStr, fileName); rc = _python_ibm_db_assign_options(handle, type, SQL_ATTR_TRUSTED_CONTEXT_PASSWORD, tc_pass); + snprintf(messageStr, sizeof(messageStr), "_python_ibm_db_assign_options for tc_pass returned: %d", rc); + LogMsg(INFO, messageStr, fileName); } - if (rc) + if (rc) { + LogMsg(INFO, "exit _python_ibm_db_parse_options()", fileName); return SQL_ERROR; + } } + LogMsg(INFO, "exit _python_ibm_db_parse_options()", fileName); return SQL_SUCCESS; } @@ -834,14 +1091,19 @@ initialize the result set information of each column. This must be done once */ static int _python_ibm_db_get_result_set_info(stmt_handle *stmt_res) { + LogMsg(INFO, "entry _python_ibm_db_get_result_set_info()", fileName); + snprintf(messageStr, sizeof(messageStr), "stmt_res pointer: %p", (void*)stmt_res); + LogMsg(DEBUG, messageStr, fileName); int rc = -1, i; SQLSMALLINT nResultCols = 0, name_length; SQLCHAR tmp_name[BUFSIZ]; - + snprintf(messageStr, sizeof(messageStr), "Calling SQLNumResultCols() with hstmt = %p", (void*)stmt_res->hstmt); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLNumResultCols((SQLHSTMT)stmt_res->hstmt, &nResultCols); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLNumResultCols() returned rc = %d, nResultCols = %d", rc, nResultCols); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || nResultCols == 0) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); @@ -852,15 +1114,21 @@ static int _python_ibm_db_get_result_set_info(stmt_handle *stmt_res) _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } */ + snprintf(messageStr, sizeof(messageStr), "Allocating memory for column_info array of size %d", nResultCols); + LogMsg(DEBUG, messageStr, fileName); stmt_res->num_columns = nResultCols; stmt_res->column_info = ALLOC_N(ibm_db_result_set_info, nResultCols); if ( stmt_res->column_info == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } memset(stmt_res->column_info, 0, sizeof(ibm_db_result_set_info)*nResultCols); /* return a set of attributes for a column */ for (i = 0 ; i < nResultCols; i++) { + snprintf(messageStr, sizeof(messageStr), "Calling SQLDescribeCol() for column %d with hstmt = %p, col_num = %d, tmp_name buffer size = %d", + i, (void*)stmt_res->hstmt, i + 1, BUFSIZ); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLDescribeCol((SQLHSTMT)stmt_res->hstmt, (SQLSMALLINT)(i + 1 ), (SQLCHAR *)&tmp_name, BUFSIZ, &name_length, @@ -869,7 +1137,14 @@ static int _python_ibm_db_get_result_set_info(stmt_handle *stmt_res) &stmt_res->column_info[i].scale, &stmt_res->column_info[i].nullable); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLDescribeCol() for column %d returned rc = %d, tmp_name = %s, name_length = %d, type = %d, size = %d, scale = %d, nullable = %d", + i, rc, tmp_name, name_length, + stmt_res->column_info[i].type, + stmt_res->column_info[i].size, + stmt_res->column_info[i].scale, + stmt_res->column_info[i].nullable); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); @@ -881,14 +1156,20 @@ static int _python_ibm_db_get_result_set_info(stmt_handle *stmt_res) if ( name_length <= 0 ) { stmt_res->column_info[i].name = (SQLCHAR *)estrdup(""); if ( stmt_res->column_info[i].name == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } } else if (name_length >= BUFSIZ ) { /* column name is longer than BUFSIZ */ + LogMsg(DEBUG, "column name is longer than BUFSIZ", fileName); + snprintf(messageStr, sizeof(messageStr), "Re-querying SQLDescribeCol() for long column name %d with hstmt = %p, name_length = %d", + i, (void*)stmt_res->hstmt, name_length); + LogMsg(DEBUG, messageStr, fileName); stmt_res->column_info[i].name = (SQLCHAR*)ALLOC_N(char, name_length+1); if ( stmt_res->column_info[i].name == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } @@ -901,7 +1182,9 @@ static int _python_ibm_db_get_result_set_info(stmt_handle *stmt_res) &stmt_res->column_info[i].scale, &stmt_res->column_info[i].nullable); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLDescribeCol() re-query for column %d returned rc = %d", + i, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); @@ -914,12 +1197,15 @@ static int _python_ibm_db_get_result_set_info(stmt_handle *stmt_res) } else { stmt_res->column_info[i].name = (SQLCHAR*)estrdup((char*)tmp_name); if ( stmt_res->column_info[i].name == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } } } + LogMsg(DEBUG, "Successfully completed _python_ibm_db_get_result_set_info()", fileName); + LogMsg(INFO, "entry _python_ibm_db_get_result_set_info()", fileName); return 0; } @@ -928,6 +1214,7 @@ static int _python_ibm_db_get_result_set_info(stmt_handle *stmt_res) */ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) { + LogMsg(INFO, "entry _python_ibm_db_bind_column_helper()", fileName); SQLINTEGER in_length = 0; SQLSMALLINT column_type; ibm_db_row_data_type *row_data; @@ -935,30 +1222,44 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) stmt_res->row_data = ALLOC_N(ibm_db_row_type, stmt_res->num_columns); if ( stmt_res->row_data == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } memset(stmt_res->row_data, 0, sizeof(ibm_db_row_type)*stmt_res->num_columns); + LogMsg(DEBUG, "Allocated memory for row_data", fileName); for (i = 0; inum_columns; i++) { column_type = stmt_res->column_info[i].type; row_data = &stmt_res->row_data[i].data; + snprintf(messageStr, sizeof(messageStr), "Processing column %d with type %d", i, column_type); + LogMsg(DEBUG, messageStr, fileName); switch(column_type) { case SQL_CHAR: case SQL_VARCHAR: case SQL_LONGVARCHAR: + snprintf(messageStr, sizeof(messageStr), + "Case SQL_CHAR/SQL_VARCHAR/SQL_LONGVARCHAR, i=%d, s_use_wchar=%d", i, stmt_res->s_use_wchar); + LogMsg(DEBUG, messageStr, fileName); if ( stmt_res->s_use_wchar == WCHAR_NO ) { in_length = stmt_res->column_info[i].size+1; row_data->str_val = (SQLCHAR *)ALLOC_N(char, in_length); if ( row_data->str_val == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory for str_val", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } + snprintf(messageStr, sizeof(messageStr), + "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_CHAR, buffer_size=%d, out_length=%p", + stmt_res->hstmt, i + 1, in_length, &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_CHAR, row_data->str_val, in_length, (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, @@ -971,13 +1272,22 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) case SQL_GRAPHIC: case SQL_VARGRAPHIC: case SQL_LONGVARGRAPHIC: + snprintf(messageStr, sizeof(messageStr), + "Case SQL_WCHAR/SQL_WVARCHAR/SQL_GRAPHIC/SQL_VARGRAPHIC/SQL_LONGVARGRAPHIC, i=%d", i); + LogMsg("DEBUG", messageStr, fileName); in_length = stmt_res->column_info[i].size+1; row_data->w_val = (SQLWCHAR *) ALLOC_N(SQLWCHAR, in_length); + snprintf(messageStr, sizeof(messageStr), + "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_WCHAR, buffer_size=%zu, out_length=%p", + stmt_res->hstmt, i + 1, in_length * sizeof(SQLWCHAR), &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_WCHAR, row_data->w_val, in_length * sizeof(SQLWCHAR), (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, @@ -988,20 +1298,28 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) case SQL_BINARY: case SQL_LONGVARBINARY: case SQL_VARBINARY: + snprintf(messageStr, sizeof(messageStr), + "Case SQL_BINARY/SQL_LONGVARBINARY/SQL_VARBINARY, i=%d, s_bin_mode=%d", i, stmt_res->s_bin_mode); + LogMsg(DEBUG, messageStr, fileName); if ( stmt_res->s_bin_mode == CONVERT ) { in_length = 2*(stmt_res->column_info[i].size)+1; row_data->str_val = (SQLCHAR *)ALLOC_N(char, in_length); if ( row_data->str_val == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory for str_val", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } - + snprintf(messageStr, sizeof(messageStr), + "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_CHAR, buffer_size=%d, out_length=%p", + stmt_res->hstmt, i + 1, in_length, &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_CHAR, row_data->str_val, in_length, (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, @@ -1011,16 +1329,21 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) in_length = stmt_res->column_info[i].size+1; row_data->str_val = (SQLCHAR *)ALLOC_N(char, in_length); if ( row_data->str_val == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory for str_val", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } - + snprintf(messageStr, sizeof(messageStr), + "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_DEFAULT, buffer_size=%d, out_length=%p", + stmt_res->hstmt, i + 1, in_length, &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_DEFAULT, row_data->str_val, in_length, (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, @@ -1031,19 +1354,28 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) case SQL_BIGINT: case SQL_DECFLOAT: + snprintf(messageStr, sizeof(messageStr), "Case SQL_BIGINT/SQL_DECFLOAT, i=%d", i); + LogMsg(DEBUG, messageStr, fileName); in_length = stmt_res->column_info[i].size+3; row_data->str_val = (SQLCHAR *)ALLOC_N(char, in_length); if ( row_data->str_val == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory for str_val", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } - + snprintf(messageStr, sizeof(messageStr), "Allocated memory for str_val with length %d", in_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), + "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_CHAR, buffer_size=%d, out_length=%p", + stmt_res->hstmt, i + 1, in_length, &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_CHAR, row_data->str_val, in_length, (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); @@ -1051,18 +1383,26 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) break; case SQL_TYPE_DATE: + snprintf(messageStr, sizeof(messageStr), "Case SQL_TYPE_DATE for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); row_data->date_val = ALLOC(DATE_STRUCT); if ( row_data->date_val == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory for date_val", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } - + snprintf(messageStr, sizeof(messageStr), "Allocated memory for date_val with size %zu", sizeof(DATE_STRUCT)); + LogMsg(DEBUG, messageStr, fileName); + snprintf(messageStr, sizeof(messageStr), "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_TYPE_DATE, buffer_size=%zu, out_length=%p", + stmt_res->hstmt, i + 1, sizeof(DATE_STRUCT), &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_TYPE_DATE, row_data->date_val, sizeof(DATE_STRUCT), (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); @@ -1070,18 +1410,26 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) break; case SQL_TYPE_TIME: + snprintf(messageStr, sizeof(messageStr), "Case SQL_TYPE_TIME for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); row_data->time_val = ALLOC(TIME_STRUCT); if ( row_data->time_val == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory for time_val", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } - + snprintf(messageStr, sizeof(messageStr), "Allocated memory for time_val with size %zu", sizeof(TIME_STRUCT)); + LogMsg(DEBUG, messageStr, fileName); + snprintf(messageStr, sizeof(messageStr), "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_TYPE_TIME, buffer_size=%zu, out_length=%p", + stmt_res->hstmt, i + 1, sizeof(TIME_STRUCT), &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_TYPE_TIME, row_data->time_val, sizeof(TIME_STRUCT), (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); @@ -1089,18 +1437,26 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) break; case SQL_TYPE_TIMESTAMP: + snprintf(messageStr, sizeof(messageStr), "Case SQL_TYPE_TIMESTAMP for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); row_data->ts_val = ALLOC(TIMESTAMP_STRUCT); if ( row_data->ts_val == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory for ts_val", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } - + snprintf(messageStr, sizeof(messageStr), "Allocated memory for ts_val with size %zu", sizeof(TIMESTAMP_STRUCT)); + LogMsg(DEBUG, messageStr, fileName); + snprintf(messageStr, sizeof(messageStr), "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_TYPE_TIMESTAMP, buffer_size=%zu, out_length=%p", + stmt_res->hstmt, i + 1, sizeof(TIMESTAMP_STRUCT), &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_TYPE_TIMESTAMP, row_data->time_val, sizeof(TIMESTAMP_STRUCT), (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); @@ -1114,14 +1470,19 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) case SQL_SMALLINT: case SQL_BOOLEAN: #endif - + snprintf(messageStr, sizeof(messageStr), "Case SQL_SMALLINT or SQL_BOOLEAN for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); + snprintf(messageStr, sizeof(messageStr), "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_DEFAULT, buffer_size=%zu, out_length=%p", + stmt_res->hstmt, i + 1, sizeof(row_data->s_val), &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_DEFAULT, &row_data->s_val, sizeof(row_data->s_val), (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, @@ -1130,14 +1491,19 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) break; case SQL_INTEGER: - + snprintf(messageStr, sizeof(messageStr), "Case SQL_INTEGER for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_DEFAULT, buffer=%p, buffer_size=%zu, out_length=%p", + stmt_res->hstmt, i + 1, &row_data->i_val, sizeof(row_data->i_val), &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_DEFAULT, &row_data->i_val, sizeof(row_data->i_val), (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for SQL_INTEGER column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, @@ -1146,14 +1512,19 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) break; case SQL_BIT: - + snprintf(messageStr, sizeof(messageStr), "Case SQL_BIT for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); + snprintf(messageStr, sizeof(messageStr), "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_LONG, buffer=%p, buffer_size=%zu, out_length=%p", + stmt_res->hstmt, i + 1, &row_data->i_val, sizeof(row_data->i_val), &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_LONG, &row_data->i_val, sizeof(row_data->i_val), (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for SQL_BIT column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, @@ -1162,14 +1533,19 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) break; case SQL_REAL: - + snprintf(messageStr, sizeof(messageStr), "Case SQL_REAL for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_FLOAT, buffer=%p, buffer_size=%zu, out_length=%p", + stmt_res->hstmt, i + 1, &row_data->r_val, sizeof(row_data->r_val), &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_FLOAT, &row_data->r_val, sizeof(row_data->r_val), (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for SQL_REAL column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, @@ -1178,14 +1554,19 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) break; case SQL_FLOAT: - + snprintf(messageStr, sizeof(messageStr), "Case SQL_FLOAT for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_DEFAULT, buffer=%p, buffer_size=%zu, out_length=%p", + stmt_res->hstmt, i + 1, &row_data->f_val, sizeof(row_data->f_val), &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_DEFAULT, &row_data->f_val, sizeof(row_data->f_val), (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for SQL_FLOAT column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, @@ -1194,14 +1575,19 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) break; case SQL_DOUBLE: - + snprintf(messageStr, sizeof(messageStr), "Case SQL_DOUBLE for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); + snprintf(messageStr, sizeof(messageStr), "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_DEFAULT, buffer=%p, buffer_size=%zu, out_length=%p", + stmt_res->hstmt, i + 1, &row_data->d_val, sizeof(row_data->d_val), &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_DEFAULT, &row_data->d_val, sizeof(row_data->d_val), (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for SQL_DOUBLE column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, @@ -1211,20 +1597,28 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) case SQL_DECIMAL: case SQL_NUMERIC: + snprintf(messageStr, sizeof(messageStr), "Case SQL_DECIMAL/SQL_NUMERIC for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); in_length = stmt_res->column_info[i].size + stmt_res->column_info[i].scale + 2 + 1; + snprintf(messageStr, sizeof(messageStr), "Allocating memory with size %lu for SQL_DECIMAL/SQL_NUMERIC column %d", in_length, i); + LogMsg(DEBUG, messageStr, fileName); row_data->str_val = (SQLCHAR *)ALLOC_N(char, in_length); if ( row_data->str_val == NULL ) { + LogMsg(EXCEPTION, "Failed to Allocate Memory for SQL_DECIMAL/SQL_NUMERIC", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return -1; } - + snprintf(messageStr, sizeof(messageStr), "Calling SQLBindCol with parameters: hstmt=%p, col=%d, sql_type=SQL_C_CHAR, buffer=%p, buffer_size=%lu, out_length=%p", + stmt_res->hstmt, i + 1, row_data->str_val, in_length, &stmt_res->row_data[i].out_length); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)(i+1), SQL_C_CHAR, row_data->str_val, in_length, (SQLINTEGER *)(&stmt_res->row_data[i].out_length)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindCol returned %d for SQL_DECIMAL/SQL_NUMERIC column %d", rc, i); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, @@ -1236,26 +1630,40 @@ static int _python_ibm_db_bind_column_helper(stmt_handle *stmt_res) case SQL_CLOB: case SQL_DBCLOB: case SQL_XML: + snprintf(messageStr, sizeof(messageStr), "Case SQL_BLOB/SQL_CLOB/SQL_DBCLOB/SQL_XML for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); stmt_res->row_data[i].out_length = 0; + snprintf(messageStr, sizeof(messageStr), "Set out_length to 0 for SQL_BLOB/SQL_CLOB/SQL_DBCLOB/SQL_XML column %d", i); + LogMsg(DEBUG, messageStr, fileName); break; default: + snprintf(messageStr, sizeof(messageStr), "Case default case for column index %d", i); + LogMsg(DEBUG, messageStr, fileName); break; } } + LogMsg(INFO, "exit _python_ibm_db_bind_column_helper()", fileName); return rc; } /* static void _python_ibm_db_clear_stmt_err_cache () */ static void _python_ibm_db_clear_stmt_err_cache(void) { + LogMsg(INFO, "entry _python_ibm_db_clear_stmt_err_cache()", fileName); memset(IBM_DB_G(__python_stmt_err_msg), 0, DB2_MAX_ERR_MSG_LEN); memset(IBM_DB_G(__python_stmt_err_state), 0, SQL_SQLSTATE_SIZE + 1); + LogMsg(INFO, "exit _python_ibm_db_clear_stmt_err_cache()", fileName); } /* static int _python_ibm_db_connect_helper( argc, argv, isPersistent ) */ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, int isPersistent ) { + LogMsg(INFO, "entry _python_ibm_db_connect_helper()", fileName); + LogMsg(DEBUG, "In process of connection", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received connection arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *databaseObj = NULL; PyObject *uidObj = NULL; PyObject *passwordObj = NULL; @@ -1277,8 +1685,12 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, PyObject *pid = NULL; conn_alive = 1; if (!PyArg_ParseTuple(args, "OOO|OO", &databaseObj, &uidObj, &passwordObj, &options, &literal_replacementObj)){ + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Parsed values: databaseObj=%p, uidObj=%p, passwordObj=%p, options=%p, literal_replacementObj=%p", + databaseObj, uidObj, passwordObj, options, literal_replacementObj); + LogMsg(DEBUG, messageStr, fileName); do { databaseObj = PyUnicode_FromObject(databaseObj); uidObj = PyUnicode_FromObject(uidObj); @@ -1289,23 +1701,26 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, */ if (isPersistent) { // we do not want to process a None type and segfault. Better safe than sorry! - if (NIL_P(databaseObj)) { - PyErr_SetString(PyExc_Exception, "Supplied Parameter is invalid"); - return NULL; - } - else if(!(PyUnicode_Contains(databaseObj, equal) > 0) && ( NIL_P(uidObj) || NIL_P(passwordObj))) - { - PyErr_SetString(PyExc_Exception, "Supplied Parameter is invalid"); - return NULL; - } - else - { - if (NIL_P(uidObj) || NIL_P(passwordObj)) - { + if (NIL_P(databaseObj)) { + LogMsg(ERROR, "Supplied Parameter is invalid", fileName); + PyErr_SetString(PyExc_Exception, "Supplied Parameter is invalid"); + return NULL; + } + else if(!(PyUnicode_Contains(databaseObj, equal) > 0) && ( NIL_P(uidObj) || NIL_P(passwordObj))) + { + LogMsg(ERROR, "Supplied Parameter is invalid", fileName); + PyErr_SetString(PyExc_Exception, "Supplied Parameter is invalid"); + return NULL; + } + else + { + if (NIL_P(uidObj) || NIL_P(passwordObj)) + { + LogMsg(ERROR, "Supplied Parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied Parameter is invalid"); - return NULL; - } - } + return NULL; + } + } hKey = PyUnicode_Concat(StringOBJ_FromASCII("__ibm_db_"), uidObj); hKey = PyUnicode_Concat(hKey, databaseObj); @@ -1313,9 +1728,12 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, pid = PyObject_CallObject(os_getpid, NULL); if (pid == NULL) { + LogMsg(EXCEPTION, "Failed to obtain current process id", fileName); PyErr_SetString(PyExc_Exception, "Failed to obtain current process id"); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Obtain process id: %p", pid); + LogMsg(INFO, messageStr, fileName); hKey = PyUnicode_Concat(hKey, PyUnicode_FromFormat("%ld", PyLong_AsLong(pid))); Py_DECREF(pid); @@ -1330,11 +1748,17 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, rc = SQLGetConnectAttr(conn_res->hdbc, SQL_ATTR_PING_DB, (SQLPOINTER)&conn_alive, 0, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLGetConnectAttr with parameters: conn_res->hdbc=%p, SQL_ATTR_PING_DB=%d, conn_alive=%d and returned rc=%d", + (void *)conn_res->hdbc, SQL_ATTR_PING_DB, conn_alive, rc); + LogMsg(DEBUG, messageStr, fileName); if ( (rc == SQL_SUCCESS) && conn_alive ) { _python_ibm_db_check_sql_errors( conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); reused = 1; } /* else will re-connect since connection is dead */ + else { + LogMsg(INFO, "Connection is dead. Reconnecting...", fileName); + } #endif /* PASE */ #if defined(__MVS__) /* Since SQL_ATTR_PING_DB is not supported by z ODBC driver, @@ -1347,34 +1771,50 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, } if ( !NIL_P(literal_replacementObj) ) { - literal_replacement = (SQLINTEGER) PyInt_AsLong(literal_replacementObj); + literal_replacement = (SQLINTEGER) PyLong_AsLong(literal_replacementObj); + snprintf(messageStr, sizeof(messageStr), "Setting literal_replacement to: %d", literal_replacement); + LogMsg(DEBUG, messageStr, fileName); } else { literal_replacement = SET_QUOTED_LITERAL_REPLACEMENT_OFF; /*QUOTED LITERAL replacemnt is OFF by default*/ + LogMsg(DEBUG, "Setting literal_replacement to SET_QUOTED_LITERAL_REPLACEMENT_OFF", fileName); } if (conn_res == NULL) { conn_res = PyObject_NEW(conn_handle, &conn_handleType); conn_res->henv = 0; conn_res->hdbc = 0; + LogMsg(DEBUG, "Created a new connection handle", fileName); } /* We need to set this early, in case we get an error below, so we know how to free the connection */ conn_res->flag_pconnect = isPersistent; + snprintf(messageStr, sizeof(messageStr), "Set flag_pconnect to: %d", conn_res->flag_pconnect); + LogMsg(DEBUG, messageStr, fileName); /* Allocate ENV handles if not present */ if ( !conn_res->henv ) { Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_ENV, SQL_NULL_HANDLE, &(conn_res->henv)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLAllocHandle called with parameters: SQL_HANDLE_ENV=%d, SQL_NULL_HANDLE=%p, &conn_res->henv=%p and returned rc=%d", + SQL_HANDLE_ENV, (void *)SQL_NULL_HANDLE, (void *)&(conn_res->henv), rc); + LogMsg(DEBUG, messageStr, fileName); if (rc != SQL_SUCCESS) { + LogMsg(ERROR, "Failed to allocate ENV handles", fileName); _python_ibm_db_check_sql_errors( conn_res->henv, SQL_HANDLE_ENV, rc, 1, NULL, -1, 1); break; } + else { + LogMsg(DEBUG, "Successfully allocated ENV handles", fileName); + } Py_BEGIN_ALLOW_THREADS; rc = SQLSetEnvAttr((SQLHENV)conn_res->henv, SQL_ATTR_ODBC_VERSION, (void *)SQL_OV_ODBC3, 0); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLSetEnvAttr called with parameters: conn_res->henv=%p, SQL_ATTR_ODBC_VERSION=%d, SQL_OV_ODBC3=%d and returned rc=%d", + (void *)conn_res->henv, SQL_ATTR_ODBC_VERSION, SQL_OV_ODBC3, rc); + LogMsg(DEBUG, messageStr, fileName); } if (!reused) { @@ -1382,11 +1822,18 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_DBC, conn_res->henv, &(conn_res->hdbc)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLAllocHandle called with parameters: SQL_HANDLE_DBC=%d, conn_res->henv=%p, &(conn_res->hdbc)=%p and returned rc=%d", + SQL_HANDLE_DBC, (void *)conn_res->henv, (void *)&(conn_res->hdbc), rc); + LogMsg(DEBUG, messageStr, fileName); if (rc != SQL_SUCCESS) { + LogMsg(ERROR, "Failed to allocate CONNECT Handle", fileName); _python_ibm_db_check_sql_errors(conn_res->henv, SQL_HANDLE_ENV, rc, 1, NULL, -1, 1); break; } + else { + LogMsg(DEBUG, "Successfully allocated CONNECT Handle", fileName); + } } /* Set this after the connection handle has been allocated to avoid @@ -1396,7 +1843,11 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, rc = SQLSetConnectAttr((SQLHDBC)conn_res->hdbc, SQL_ATTR_AUTOCOMMIT, (SQLPOINTER)(conn_res->auto_commit), SQL_NTS); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "Set auto_commit to: %d", conn_res->auto_commit); + LogMsg(DEBUG, messageStr, fileName); + snprintf(messageStr, sizeof(messageStr), "SQLSetConnectAttr called with parameters: conn_res->hdbc=%p, SQL_ATTR_AUTOCOMMIT=%d, conn_res->auto_commit=%d, SQL_NTS=%d and returned rc=%d", + (void *)conn_res->hdbc, SQL_ATTR_AUTOCOMMIT, conn_res->auto_commit, SQL_NTS, rc); + LogMsg(DEBUG, messageStr, fileName); conn_res->c_bin_mode = IBM_DB_G(bin_mode); conn_res->c_case_mode = CASE_NATURAL; conn_res->c_use_wchar = WCHAR_YES; @@ -1411,35 +1862,47 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, /* Set Options */ if ( !NIL_P(options) ) { if(!PyDict_Check(options)) { + LogMsg(EXCEPTION, "options Parameter must be of type dictionay", fileName); PyErr_SetString(PyExc_Exception, "options Parameter must be of type dictionay"); return NULL; } rc = _python_ibm_db_parse_options( options, SQL_HANDLE_DBC, conn_res ); if (rc != SQL_SUCCESS) { + LogMsg(ERROR, "Failed to parse options", fileName); Py_BEGIN_ALLOW_THREADS; SQLFreeHandle(SQL_HANDLE_DBC, conn_res->hdbc); SQLFreeHandle(SQL_HANDLE_ENV, conn_res->henv); Py_END_ALLOW_THREADS; break; } + else { + LogMsg(DEBUG, "Successfully parsed options", fileName); + } } if (! reused) { /* Connect */ /* If the string contains a =, use SQLDriverConnect */ if (NIL_P(databaseObj)) { + LogMsg(ERROR, "Invalid database parameter", fileName); PyErr_SetString(PyExc_Exception, "Supplied Parameter is invalid"); return NULL; } database = getUnicodeDataAsSQLWCHAR(databaseObj, &isNewBuffer); if ( PyUnicode_Contains(databaseObj, equal) > 0 ) { + LogMsg(DEBUG, "Using SQLDriverConnectW for connection", fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLDriverConnectW((SQLHDBC)conn_res->hdbc, (SQLHWND)NULL, database, SQL_NTS, NULL, 0, NULL, SQL_DRIVER_NOPROMPT ); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLDriverConnectW called with parameters: conn_res->hdbc=%p, SQLHWND=NULL, database=%ls, SQL_NTS=%d, NULL, 0, NULL, SQL_DRIVER_NOPROMPT=%d and returned rc=%d", + (void *)conn_res->hdbc, database, SQL_NTS, SQL_DRIVER_NOPROMPT, rc); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(DEBUG, "Using SQLConnectW for connection", fileName); if (NIL_P(uidObj) || NIL_P(passwordObj)) { + LogMsg(ERROR, "Invalid uid or password parameter", fileName); PyErr_SetString(PyExc_Exception, "Supplied Parameter is invalid"); return NULL; } @@ -1454,6 +1917,12 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, PyUnicode_GetLength(uidObj)*2, password, PyUnicode_GetLength(passwordObj)*2); + snprintf(messageStr, sizeof(messageStr), "SQLConnectW called with parameters: conn_res->hdbc=%p, database=%ls, databaseLen=%zd, uid=%ls, uidLen=%zd, password=%ls, passwordLen=%zd and returned rc=%d", + (void *)conn_res->hdbc, database, + PyUnicode_GetLength(databaseObj)*2, uid, + PyUnicode_GetLength(uidObj)*2, password, + PyUnicode_GetLength(passwordObj)*2, rc); + LogMsg(DEBUG, messageStr, fileName); #else rc = SQLConnectW((SQLHDBC)conn_res->hdbc, database, @@ -1462,15 +1931,23 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, PyUnicode_GetLength(uidObj), password, PyUnicode_GetLength(passwordObj)); + snprintf(messageStr, sizeof(messageStr), "SQLConnectW called with parameters: conn_res->hdbc=%p, database=%ls, databaseLen=%zd, uid=%ls, uidLen=%zd, password=%ls, passwordLen=%zd and returned rc=%d", + (void *)conn_res->hdbc, database, + PyUnicode_GetLength(databaseObj), uid, + PyUnicode_GetLength(uidObj), password, + PyUnicode_GetLength(passwordObj), rc); + LogMsg(DEBUG, messageStr, fileName); #endif Py_END_ALLOW_THREADS; } if( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { + LogMsg(DEBUG, "Checking SQL connection errors", fileName); _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc,1, NULL, -1, 1); } if ( rc == SQL_ERROR ) { + LogMsg(ERROR, "Failed to connect to database", fileName); Py_BEGIN_ALLOW_THREADS; SQLFreeHandle(SQL_HANDLE_DBC, conn_res->hdbc); SQLFreeHandle(SQL_HANDLE_ENV, conn_res->henv); @@ -1484,9 +1961,11 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, * Code for setting SQL_ATTR_DECFLOAT_ROUNDING_MODE * for implementation of Decfloat Datatype */ + LogMsg(DEBUG, "Setting SQL_ATTR_DECFLOAT_ROUNDING_MODE", fileName); rc = _python_ibm_db_set_decfloat_rounding_mode_client(conn_res->hdbc); if (rc != SQL_SUCCESS){ + LogMsg(ERROR, "Failed to set SQL_ATTR_DECFLOAT_ROUNDING_MODE", fileName); _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } @@ -1494,15 +1973,24 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, #endif /* Get the server name */ + LogMsg(INFO, "Getting server name", fileName); memset(server, 0, sizeof(server)); Py_BEGIN_ALLOW_THREADS; rc = SQLGetInfo(conn_res->hdbc, SQL_DBMS_NAME, (SQLPOINTER)server, 2048, NULL); Py_END_ALLOW_THREADS; - - if (!strcmp(server, "AS")) is_systemi = 1; - if (!strncmp(server, "IDS", 3)) is_informix = 1; + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters: conn_res->hdbc=%p, SQL_DBMS_NAME=%d, server=%s, 2048 and returned rc=%d", + (void *)conn_res->hdbc, SQL_DBMS_NAME, server, rc); + LogMsg(DEBUG, messageStr, fileName); + if (!strcmp(server, "AS")){ + LogMsg(INFO, "Server identified as AS", fileName); + is_systemi = 1; + } + if (!strncmp(server, "IDS", 3)) { + LogMsg(INFO, "Server identified as Informix", fileName); + is_informix = 1; + } /* Set SQL_ATTR_REPLACE_QUOTED_LITERALS connection attribute to * enable CLI numeric literal feature. This is equivalent to @@ -1515,21 +2003,31 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, * server */ if (!is_informix && (literal_replacement == SET_QUOTED_LITERAL_REPLACEMENT_ON)) { + LogMsg(DEBUG, "Enabling SQL_ATTR_REPLACE_QUOTED_LITERALS", fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLSetConnectAttr((SQLHDBC)conn_res->hdbc, SQL_ATTR_REPLACE_QUOTED_LITERALS, (SQLPOINTER) (ENABLE_NUMERIC_LITERALS), SQL_IS_INTEGER); Py_END_ALLOW_THREADS; - if (rc != SQL_SUCCESS) + snprintf(messageStr, sizeof(messageStr), "SQLSetConnectAttr called with parameters: conn_res->hdbc=%p, SQL_ATTR_REPLACE_QUOTED_LITERALS=%d, ENABLE_NUMERIC_LITERALS=%d, SQL_IS_INTEGER=%d and returned rc=%d", + (void *)conn_res->hdbc, SQL_ATTR_REPLACE_QUOTED_LITERALS, ENABLE_NUMERIC_LITERALS, SQL_IS_INTEGER, rc); + LogMsg(DEBUG, messageStr, fileName); + if (rc != SQL_SUCCESS) { + LogMsg(ERROR, "Failed to set SQL_ATTR_REPLACE_QUOTED_LITERALS", fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLSetConnectAttr((SQLHDBC)conn_res->hdbc, SQL_ATTR_REPLACE_QUOTED_LITERALS_OLDVALUE, (SQLPOINTER)(ENABLE_NUMERIC_LITERALS), SQL_IS_INTEGER); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLSetConnectAttr called with parameters: conn_res->hdbc=%p, SQL_ATTR_REPLACE_QUOTED_LITERALS_OLDVALUE=%d, ENABLE_NUMERIC_LITERALS=%d, SQL_IS_INTEGER=%d and returned rc=%d", + (void *)conn_res->hdbc, SQL_ATTR_REPLACE_QUOTED_LITERALS_OLDVALUE, ENABLE_NUMERIC_LITERALS, SQL_IS_INTEGER, rc); + LogMsg(DEBUG, messageStr, fileName); + } } if (rc != SQL_SUCCESS) { + LogMsg(ERROR, "Failed to set connection attributes", fileName); _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } @@ -1545,6 +2043,7 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, /* If we created a new persistent connection, add it to the * persistent_list */ + LogMsg(DEBUG, "Adding connection to persistent_list", fileName); PyDict_SetItem(persistent_list, hKey, (PyObject *)conn_res); } Py_DECREF(hKey); @@ -1566,8 +2065,16 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, if (conn_res != NULL) { PyObject_Del(conn_res); } + LogMsg(ERROR, "Failed to establish connection!", fileName); return NULL; } + LogMsg(INFO, "Connection successfully established!", fileName); + LogMsg(INFO, "exit _python_ibm_db_connect_helper()", fileName); + if(isPersistent) { + LogMsg(INFO, "exit pconnect()", fileName); + } else { + LogMsg(INFO, "exit connect()", fileName); + } return (PyObject *)conn_res; } @@ -1581,40 +2088,68 @@ static PyObject *_python_ibm_db_connect_helper( PyObject *self, PyObject *args, **/ static PyObject* getSQLWCharAsPyUnicodeObject(SQLWCHAR* sqlwcharData, int sqlwcharBytesLen) { + LogMsg(INFO, "entry getSQLWCharAsPyUnicodeObject()", fileName); + snprintf(messageStr, sizeof(messageStr), "sqlwcharData=%p, sqlwcharBytesLen=%d", (void*)sqlwcharData, sqlwcharBytesLen); + LogMsg(DEBUG, messageStr, fileName); PyObject *sysmodule = NULL, *maxuni = NULL; long maxuniValue; PyObject* u; sysmodule = PyImport_ImportModule("sys"); maxuni = PyObject_GetAttrString(sysmodule, "maxunicode"); - maxuniValue = PyInt_AsLong(maxuni); + maxuniValue = PyLong_AsLong(maxuni); + snprintf(messageStr, sizeof(messageStr), "sysmodule obtained: %p, maxuni obtained: %p, maxuniValue: %ld", + (void*)sysmodule, (void *)maxuni, maxuniValue); + LogMsg(DEBUG, messageStr, fileName); if (maxuniValue <= 65536) { /* this is UCS2 python.. nothing to do really */ + LogMsg(DEBUG, "Python is UCS2, using PyUnicode_FromWideChar", fileName); + PyObject *result = PyUnicode_FromWideChar((Py_UNICODE *)sqlwcharData, sqlwcharBytesLen / sizeof(SQLWCHAR)); + snprintf(messageStr, sizeof(messageStr), "UCS2 conversion result: %p", (void*)result); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit getSQLWCharAsPyUnicodeObject()", fileName); return PyUnicode_FromWideChar((Py_UNICODE *)sqlwcharData, sqlwcharBytesLen / sizeof(SQLWCHAR)); } if (is_bigendian()) { int bo = 1; + LogMsg(INFO, "Big endian detected, decoding UTF16", fileName); u = PyUnicode_DecodeUTF16((char *)sqlwcharData, sqlwcharBytesLen, "strict", &bo); + snprintf(messageStr, sizeof(messageStr), "UTF16 decoding result: %p, byteorder: %d", (void*)u, bo); + LogMsg(DEBUG, messageStr, fileName); } else { int bo = -1; + LogMsg(INFO, "Little endian detected, decoding UTF16", fileName); u = PyUnicode_DecodeUTF16((char *)sqlwcharData, sqlwcharBytesLen, "strict", &bo); + snprintf(messageStr, sizeof(messageStr), "UTF16 decoding result: %p, byteorder: %d", (void*)u, bo); + LogMsg(DEBUG, messageStr, fileName); } + LogMsg(INFO, "exit getSQLWCharAsPyUnicodeObject()", fileName); return u; } static SQLCHAR* getUnicodeDataAsSQLCHAR(PyObject *pyobj, int *isNewBuffer) { + LogMsg(INFO, "entry getUnicodeDataAsSQLCHAR()", fileName); + snprintf(messageStr, sizeof(messageStr), "pyobj=%p, isNewBuffer=%p", (void*)pyobj, (void*)isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); SQLCHAR* pNewBuffer = NULL; PyObject* pyBytesobj = PyUnicode_AsUTF8String(pyobj); int nCharLen = PyBytes_GET_SIZE(pyBytesobj); + snprintf(messageStr, sizeof(messageStr), "pyBytesobj obtained: %p, Number of bytes (nCharLen): %d", (void*)pyBytesobj, nCharLen); + LogMsg(DEBUG, messageStr, fileName); *isNewBuffer = 1; pNewBuffer = (SQLCHAR *)ALLOC_N(SQLCHAR, nCharLen + 1); + snprintf(messageStr, sizeof(messageStr), "Allocated new buffer: pNewBuffer=%p, size=%d", (void*)pNewBuffer, nCharLen + 1); + LogMsg(DEBUG, messageStr, fileName); memset(pNewBuffer, 0, sizeof(SQLCHAR) * (nCharLen + 1)); memcpy(pNewBuffer, PyBytes_AsString(pyBytesobj), sizeof(SQLCHAR) * (nCharLen) ); + LogMsg(DEBUG, "Buffer filled with data from pyBytesobj", fileName); Py_DECREF(pyBytesobj); + LogMsg(DEBUG, "Decremented reference count for pyBytesobj, now returning pNewBuffer", fileName); + LogMsg(INFO, "exit getUnicodeDataAsSQLCHAR()", fileName); return pNewBuffer; } @@ -1624,31 +2159,52 @@ static SQLCHAR* getUnicodeDataAsSQLCHAR(PyObject *pyobj, int *isNewBuffer) **/ static SQLWCHAR* getUnicodeDataAsSQLWCHAR(PyObject *pyobj, int *isNewBuffer) { + LogMsg(INFO, "entry getUnicodeDataAsSQLWCHAR()", fileName); + snprintf(messageStr, sizeof(messageStr), "pyobj=%p, isNewBuffer=%p", (void*)pyobj, (void*)isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); PyObject *sysmodule = NULL, *maxuni = NULL; long maxuniValue; PyObject *pyUTFobj; SQLWCHAR* pNewBuffer = NULL; int nCharLen = PyUnicode_GET_LENGTH(pyobj); - + snprintf(messageStr, sizeof(messageStr), "Unicode length (nCharLen): %d", nCharLen); + LogMsg(DEBUG, messageStr, fileName); sysmodule = PyImport_ImportModule("sys"); maxuni = PyObject_GetAttrString(sysmodule, "maxunicode"); - maxuniValue = PyInt_AsLong(maxuni); - + maxuniValue = PyLong_AsLong(maxuni); + snprintf(messageStr, sizeof(messageStr), "sysmodule obtained: %p, maxuni obtained: %p, maxuniValue: %ld", (void*)sysmodule, (void*)maxuni, maxuniValue); + LogMsg(DEBUG, messageStr, fileName); if (maxuniValue <= 65536) { *isNewBuffer = 0; + PyObject *result = (SQLWCHAR*)PyUnicode_AsWideCharString(pyobj, maxuniValue); + snprintf(messageStr, sizeof(messageStr), " result obtained: %p", (void*)result); + LogMsg(DEBUG, "UCS2 case:", fileName); + LogMsg(INFO, "exit getUnicodeDataAsSQLWCHAR()", fileName); return (SQLWCHAR*)PyUnicode_AsWideCharString(pyobj,maxuniValue); } *isNewBuffer = 1; pNewBuffer = (SQLWCHAR *)ALLOC_N(SQLWCHAR, nCharLen + 1); + snprintf(messageStr, sizeof(messageStr), "Allocated new buffer: pNewBuffer=%p, size=%d", (void*)pNewBuffer, nCharLen + 1); + LogMsg(DEBUG, messageStr, fileName); memset(pNewBuffer, 0, sizeof(SQLWCHAR) * (nCharLen + 1)); + LogMsg(DEBUG, "Buffer initialized to zero", fileName); if (is_bigendian()) { pyUTFobj = PyCodec_Encode(pyobj, "utf-16-be", "strict"); + snprintf(messageStr, sizeof(messageStr), "Encoded to UTF-16 Big Endian: pyUTFobj=%p", (void*)pyUTFobj); + LogMsg(DEBUG, messageStr, fileName); } else { pyUTFobj = PyCodec_Encode(pyobj, "utf-16-le", "strict"); + snprintf(messageStr, sizeof(messageStr), "Encoded to UTF-16 Little Endian: pyUTFobj=%p", (void*)pyUTFobj); + LogMsg(DEBUG, messageStr, fileName); } memcpy(pNewBuffer, PyBytes_AsString(pyUTFobj), sizeof(SQLWCHAR) * (nCharLen) ); + snprintf(messageStr, sizeof(messageStr), "Copied data to pNewBuffer: pNewBuffer=%p", (void*)pNewBuffer); + LogMsg(DEBUG, messageStr, fileName); Py_DECREF(pyUTFobj); + Py_DECREF(sysmodule); + LogMsg(DEBUG, "Decremented reference count for pyUTFobj", fileName); + LogMsg(INFO, "exit getUnicodeDataAsSQLWCHAR()", fileName); return pNewBuffer; } @@ -1671,6 +2227,7 @@ static SQLWCHAR* getUnicodeDataAsSQLWCHAR(PyObject *pyobj, int *isNewBuffer) * */ static int _python_ibm_db_set_decfloat_rounding_mode_client(SQLHANDLE hdbc) { + LogMsg(INFO, "entry _python_ibm_db_set_decfloat_rounding_mode_client()", fileName); SQLCHAR decflt_rounding[20]; SQLHANDLE hstmt; int rc = 0; @@ -1681,19 +2238,26 @@ static int _python_ibm_db_set_decfloat_rounding_mode_client(SQLHANDLE hdbc) SQLCHAR *stmt = (SQLCHAR *)"values current decfloat rounding mode"; /* Allocate a Statement Handle */ + snprintf(messageStr, sizeof(messageStr), "Calling SQLAllocHandle with SQL_HANDLE_STMT, hdbc=%p, hstmt=%p", + (void *)hdbc, (void *)hstmt); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, hdbc, &hstmt); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLAllocHandle result: rc=%d, hstmt=%p", rc, (void *)hstmt); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); return rc; } - + snprintf(messageStr, sizeof(messageStr), "Executing SQL statement: %s", stmt); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLExecDirect((SQLHSTMT)hstmt, stmt, SQL_NTS); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLExecDirect result: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors((SQLHSTMT)hstmt, @@ -1703,10 +2267,15 @@ static int _python_ibm_db_set_decfloat_rounding_mode_client(SQLHANDLE hdbc) if ( rc == SQL_ERROR ) { return rc; } - + snprintf(messageStr, sizeof(messageStr), + "Calling SQLBindCol with hstmt=%p, column_number=%d, C_type=%d, buffer=%p, buffer_length=%zu, indicator=NULL", + (void *)hstmt, 1, SQL_C_DEFAULT, (void *)decflt_rounding, sizeof(decflt_rounding)); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindCol((SQLHSTMT)hstmt, 1, SQL_C_DEFAULT, decflt_rounding, 20, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLBindCol result: rc=%d, bound_column_value='%s'", rc, decflt_rounding); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)hstmt, @@ -1714,7 +2283,8 @@ static int _python_ibm_db_set_decfloat_rounding_mode_client(SQLHANDLE hdbc) -1, 1); return rc; } - + snprintf(messageStr, sizeof(messageStr), "Calling SQLFetch on hstmt=%p", (void *)hstmt); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFetch(hstmt); if (rc == SQL_SUCCESS_WITH_INFO ) @@ -1724,18 +2294,29 @@ static int _python_ibm_db_set_decfloat_rounding_mode_client(SQLHANDLE hdbc) -1 ,1); } Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLFetch result: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); + snprintf(messageStr, sizeof(messageStr), "Calling SQLFreeHandle with SQL_HANDLE_STMT, hstmt=%p", (void *)hstmt); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFreeHandle(SQL_HANDLE_STMT, hstmt); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLFreeHandle result: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); /* Now setting up the same rounding mode on the client*/ if (strcmp(decflt_rounding, "ROUND_HALF_EVEN") == 0) rounding_mode = ROUND_HALF_EVEN; if (strcmp(decflt_rounding, "ROUND_HALF_UP") == 0) rounding_mode = ROUND_HALF_UP; if (strcmp(decflt_rounding, "ROUND_DOWN") == 0) rounding_mode = ROUND_DOWN; if (strcmp(decflt_rounding, "ROUND_CEILING") == 0) rounding_mode = ROUND_CEILING; if (strcmp(decflt_rounding, "ROUND_FLOOR") == 0) rounding_mode = ROUND_FLOOR; - + + snprintf(messageStr, sizeof(messageStr), "Setting client rounding mode to: %d", rounding_mode); + LogMsg(DEBUG, messageStr, fileName); + + snprintf(messageStr, sizeof(messageStr), + "Calling SQLSetConnectAttr with SQL_ATTR_DECFLOAT_ROUNDING_MODE, rounding_mode=%d", rounding_mode); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; #ifndef PASE rc = SQLSetConnectAttr(hdbc, SQL_ATTR_DECFLOAT_ROUNDING_MODE, (SQLPOINTER)rounding_mode, SQL_NTS); @@ -1743,7 +2324,9 @@ static int _python_ibm_db_set_decfloat_rounding_mode_client(SQLHANDLE hdbc) rc = SQLSetConnectAttr(hdbc, SQL_ATTR_DECFLOAT_ROUNDING_MODE, (SQLPOINTER)&rounding_mode, SQL_NTS); #endif Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLSetConnectAttr result: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit _python_ibm_db_set_decfloat_rounding_mode_client()", fileName); return rc; } @@ -1754,8 +2337,10 @@ static int _python_ibm_db_set_decfloat_rounding_mode_client(SQLHANDLE hdbc) static void _python_ibm_db_clear_conn_err_cache(void) { /* Clear out the cached conn messages */ + LogMsg(INFO, "entry _python_ibm_db_clear_conn_err_cache()", fileName); memset(IBM_DB_G(__python_conn_err_msg), 0, DB2_MAX_ERR_MSG_LEN); memset(IBM_DB_G(__python_conn_err_state), 0, SQL_SQLSTATE_SIZE + 1); + LogMsg(INFO, "exit _python_ibm_db_clear_conn_err_cache()", fileName); } /*!# @@ -1904,6 +2489,7 @@ static void _python_ibm_db_clear_conn_err_cache(void) */ static PyObject *ibm_db_connect(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry connect()", fileName); _python_ibm_db_clear_conn_err_cache(); return _python_ibm_db_connect_helper( self, args, 0 ); } @@ -1976,6 +2562,7 @@ static PyObject *ibm_db_connect(PyObject *self, PyObject *args) */ static PyObject *ibm_db_pconnect(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry pconnect()", fileName); _python_ibm_db_clear_conn_err_cache(); return _python_ibm_db_connect_helper( self, args, 1); } @@ -1985,6 +2572,11 @@ static PyObject *ibm_db_pconnect(PyObject *self, PyObject *args) */ static void _python_clear_local_var(PyObject *dbNameObj, SQLWCHAR *dbName, PyObject *codesetObj, SQLWCHAR *codeset, PyObject *modeObj, SQLWCHAR *mode, int isNewBuffer) { + LogMsg(INFO, "entry _python_clear_local_var()", fileName); + snprintf(messageStr, sizeof(messageStr), + "Before clearing: dbNameObj=%p, dbName=%p, codesetObj=%p, codeset=%p, modeObj=%p, mode=%p", + (void *)dbNameObj, (void *)dbName, (void *)codesetObj, (void *)codeset, (void *)modeObj, (void *)mode); + LogMsg(DEBUG, messageStr, fileName); if ( !NIL_P( dbNameObj ) ) { Py_XDECREF( dbNameObj ); if ( isNewBuffer ) { @@ -2005,6 +2597,11 @@ static void _python_clear_local_var(PyObject *dbNameObj, SQLWCHAR *dbName, PyObj PyMem_Del( mode ); } } + snprintf(messageStr, sizeof(messageStr), + "After clearing: dbNameObj=%p, dbName=%p, codesetObj=%p, codeset=%p, modeObj=%p, mode=%p", + (void *)dbNameObj, (void *)dbName, (void *)codesetObj, (void *)codeset, (void *)modeObj, (void *)mode); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit _python_clear_local_var()", fileName); } /* @@ -2012,6 +2609,7 @@ static void _python_clear_local_var(PyObject *dbNameObj, SQLWCHAR *dbName, PyObj */ static int _python_ibm_db_createdb(conn_handle *conn_res, PyObject *dbNameObj, PyObject *codesetObj, PyObject *modeObj, int createNX) { + LogMsg(INFO, "entry _python_ibm_db_createdb()", fileName); SQLWCHAR *dbName = NULL; SQLWCHAR *codeset = NULL; SQLWCHAR *mode = NULL; @@ -2031,17 +2629,22 @@ static int _python_ibm_db_createdb(conn_handle *conn_res, PyObject *dbNameObj, P #endif #if defined(__MVS__) + LogMsg(ERROR, "Not supported: This function is not supported on this platform", fileName); PyErr_SetString( PyExc_Exception, "Not supported: This function not supported on this platform" ); return -1; #endif if ( !NIL_P( conn_res ) ) { + snprintf(messageStr, sizeof(messageStr), "Connection resource is valid, handle_active=%d", conn_res->handle_active); + LogMsg(INFO, messageStr, fileName); if ( NIL_P( dbNameObj ) ) { + LogMsg(ERROR, "Supplied database name parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied database name Parameter is invalid" ); return -1; } /* Check to ensure the connection resource given is active */ if ( !conn_res->handle_active ) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString( PyExc_Exception, "Connection is not active" ); return -1; } @@ -2049,7 +2652,10 @@ static int _python_ibm_db_createdb(conn_handle *conn_res, PyObject *dbNameObj, P dbNameObj = PyUnicode_FromObject( dbNameObj ); if ( dbNameObj != NULL && dbNameObj != Py_None ) { dbName = getUnicodeDataAsSQLWCHAR( dbNameObj, &isNewBuffer ); + snprintf(messageStr, sizeof(messageStr), "dbName obtained, dbName=%ls, isNewBuffer=%d", dbName, isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Failed to convert dbNameObj to SQLWCHAR", fileName); return -1; } @@ -2057,7 +2663,10 @@ static int _python_ibm_db_createdb(conn_handle *conn_res, PyObject *dbNameObj, P codesetObj = PyUnicode_FromObject( codesetObj ); if ( codesetObj != NULL && codesetObj != Py_None ) { codeset = getUnicodeDataAsSQLWCHAR( codesetObj, &isNewBuffer ); + snprintf(messageStr, sizeof(messageStr), "codeset obtained, codeset=%ls, isNewBuffer=%d", codeset, isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Failed to convert codesetObj to SQLWCHAR", fileName); _python_clear_local_var( dbNameObj, dbName, NULL, NULL, NULL, NULL, isNewBuffer ); return -1; } @@ -2067,7 +2676,10 @@ static int _python_ibm_db_createdb(conn_handle *conn_res, PyObject *dbNameObj, P modeObj = PyUnicode_FromObject( modeObj ); if ( codesetObj != NULL && codesetObj != Py_None ) { mode = getUnicodeDataAsSQLWCHAR( modeObj, &isNewBuffer ); + snprintf(messageStr, sizeof(messageStr), "mode obtained, mode=%ls, isNewBuffer=%d", mode, isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Failed to convert modeObj to SQLWCHAR", fileName); _python_clear_local_var( dbNameObj, dbName, codesetObj, codeset, NULL, NULL, isNewBuffer ); return -1; } @@ -2083,6 +2695,7 @@ static int _python_ibm_db_createdb(conn_handle *conn_res, PyObject *dbNameObj, P #endif if ( !cliLib ) { sprintf( (char *)msg, "Error in loading %s library file", LIBDB2 ); + LogMsg(ERROR, (char *)msg, fileName); PyErr_SetString( PyExc_Exception, (char *)msg ); _python_clear_local_var( dbNameObj, dbName, codesetObj, codeset, modeObj, mode, isNewBuffer ); return -1; @@ -2095,12 +2708,15 @@ static int _python_ibm_db_createdb(conn_handle *conn_res, PyObject *dbNameObj, P sqlcreatedb = (sqlcreatedbType) DLSYM( cliLib, "SQLCreateDbW" ); #endif Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Function pointer sqlcreatedb resolved to address=%p", (void *)sqlcreatedb); + LogMsg(DEBUG, messageStr, fileName); if ( sqlcreatedb == NULL ) { #ifdef _WIN32 sprintf( (char *)msg, "Not supported: This function is only supported from v97fp4 version of cli on window" ); #else sprintf( (char *)msg, "Not supported: This function is only supported from v97fp3 version of cli" ); #endif + LogMsg(ERROR, (char *)msg, fileName); PyErr_SetString( PyExc_Exception, (char *)msg ); DLCLOSE( cliLib ); _python_clear_local_var( dbNameObj, dbName, codesetObj, codeset, modeObj, mode, isNewBuffer ); @@ -2111,10 +2727,15 @@ static int _python_ibm_db_createdb(conn_handle *conn_res, PyObject *dbNameObj, P rc = (*sqlcreatedb)( (SQLHDBC)conn_res->hdbc, dbName, SQL_NTS, codeset, SQL_NTS, mode, SQL_NTS ); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLCreateDbW call returned rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); + DLCLOSE( cliLib ); if ( rc != SQL_SUCCESS ) { if ( createNX == 1 ) { if ( SQLGetDiagRec( SQL_HANDLE_DBC, (SQLHDBC)conn_res->hdbc, 1, sqlstate, &sqlcode, msg, SQL_MAX_MESSAGE_LENGTH + 1, &length ) == SQL_SUCCESS ) { + snprintf(messageStr, sizeof(messageStr), "SQLGetDiagRec returned sqlcode=%d, sqlstate=%s, msg=%s", sqlcode, sqlstate, msg); + LogMsg(DEBUG, messageStr, fileName); if ( sqlcode == -1005 ) { _python_clear_local_var( dbNameObj, dbName, codesetObj, codeset, modeObj, mode, isNewBuffer ); return 0; @@ -2126,8 +2747,12 @@ static int _python_ibm_db_createdb(conn_handle *conn_res, PyObject *dbNameObj, P return -1; } _python_clear_local_var( dbNameObj, dbName, codesetObj, codeset, modeObj, mode, isNewBuffer ); + LogMsg(INFO, "Database creation process completed successfully", fileName); + LogMsg(INFO, "exit _python_ibm_db_createdb()", fileName); return 0; } else { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); + LogMsg(INFO, "exit _python_ibm_db_createdb()", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return -1; } @@ -2138,6 +2763,7 @@ static int _python_ibm_db_createdb(conn_handle *conn_res, PyObject *dbNameObj, P */ static int _python_ibm_db_dropdb(conn_handle *conn_res, PyObject *dbNameObj, int recreate) { + LogMsg(INFO, "entry _python_ibm_db_dropdb()", fileName); SQLWCHAR *dbName = NULL; SQLINTEGER sqlcode; SQLSMALLINT length; @@ -2155,17 +2781,22 @@ static int _python_ibm_db_dropdb(conn_handle *conn_res, PyObject *dbNameObj, int #endif #if defined(__MVS__) + LogMsg(ERROR, "Not supported: This function is not supported on this platform", fileName); PyErr_SetString( PyExc_Exception, "Not supported: This function not supported on this platform" ); return -1; #endif if ( !NIL_P( conn_res ) ) { + snprintf(messageStr, sizeof(messageStr), "Connection resource is valid, handle_active=%d", conn_res->handle_active); + LogMsg(INFO, messageStr, fileName); if ( NIL_P( dbNameObj ) ) { + LogMsg(ERROR, "Supplied database name parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied database name Parameter is invalid" ); return -1; } /* Check to ensure the connection resource given is active */ if ( !conn_res->handle_active ) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString( PyExc_Exception, "Connection is not active" ); return -1; } @@ -2173,7 +2804,10 @@ static int _python_ibm_db_dropdb(conn_handle *conn_res, PyObject *dbNameObj, int dbNameObj = PyUnicode_FromObject( dbNameObj ); if ( dbNameObj != NULL && dbNameObj != Py_None ) { dbName = getUnicodeDataAsSQLWCHAR( dbNameObj, &isNewBuffer ); + snprintf(messageStr, sizeof(messageStr), "dbName obtained, dbName=%ls, isNewBuffer=%d", dbName, isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Failed to convert dbNameObj to SQLWCHAR", fileName); return -1; } #ifndef __MVS__ @@ -2186,6 +2820,7 @@ static int _python_ibm_db_dropdb(conn_handle *conn_res, PyObject *dbNameObj, int #endif if ( !cliLib ) { sprintf( (char *)msg, "Error in loading %s library file", LIBDB2 ); + LogMsg(ERROR, (char *)msg, fileName); PyErr_SetString( PyExc_Exception, (char *)msg ); _python_clear_local_var( dbNameObj, dbName, NULL, NULL, NULL, NULL, isNewBuffer ); return -1; @@ -2198,12 +2833,15 @@ static int _python_ibm_db_dropdb(conn_handle *conn_res, PyObject *dbNameObj, int sqldropdb = (sqldropdbType)DLSYM( cliLib, "SQLDropDbW" ); #endif Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Function pointer sqldropdb resolved to address=%p", (void *)sqldropdb); + LogMsg(DEBUG, messageStr, fileName); if ( sqldropdb == NULL) { #ifdef _WIN32 sprintf( (char *)msg, "Not supported: This function is only supported from v97fp4 version of cli on window" ); #else sprintf( (char *)msg, "Not supported: This function is only supported from v97fp3 version of cli" ); #endif + LogMsg(ERROR, (char *)msg, fileName); PyErr_SetString( PyExc_Exception, (char *)msg ); DLCLOSE( cliLib ); _python_clear_local_var( dbNameObj, dbName, NULL, NULL, NULL, NULL, isNewBuffer ); @@ -2214,10 +2852,14 @@ static int _python_ibm_db_dropdb(conn_handle *conn_res, PyObject *dbNameObj, int rc = sqldropdb( conn_res->hdbc, dbName, SQL_NTS ); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "sqldropdb call returned rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); DLCLOSE( cliLib ); if ( rc != SQL_SUCCESS ) { if ( recreate ) { if ( SQLGetDiagRec( SQL_HANDLE_DBC, (SQLHDBC)conn_res->hdbc, 1, sqlstate, &sqlcode, msg, SQL_MAX_MESSAGE_LENGTH + 1, &length ) == SQL_SUCCESS ) { + snprintf(messageStr, sizeof(messageStr), "SQLGetDiagRec returned sqlcode=%d, sqlstate=%s, msg=%s", sqlcode, sqlstate, msg); + LogMsg(DEBUG, messageStr, fileName); if ( sqlcode == -1013 ) { _python_clear_local_var( dbNameObj, dbName, NULL, NULL, NULL, NULL, isNewBuffer ); return 0; @@ -2225,16 +2867,51 @@ static int _python_ibm_db_dropdb(conn_handle *conn_res, PyObject *dbNameObj, int } } _python_ibm_db_check_sql_errors( conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1 ); + LogMsg(INFO, "exit _python_ibm_db_dropdb()", fileName); return -1; } _python_clear_local_var( dbNameObj, dbName, NULL, NULL, NULL, NULL, isNewBuffer ); + LogMsg(INFO, "Database drop process completed successfully", fileName); + LogMsg(INFO, "exit _python_ibm_db_dropdb()", fileName); return 0; } else { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return -1; } } +static void _python_ibm_db_debug(PyObject *self, PyObject *args) +{ + PyObject *arg = NULL; + debug_mode = 0; // 0 means false by default + fileName = NULL; + + if (!PyArg_ParseTuple(args, "O", &arg)) { + } + + // Check if the argument is a boolean + if (PyBool_Check(arg)) { + debug_mode = PyObject_IsTrue(arg); + } + // Check if the argument is a string + else if (PyUnicode_Check(arg)) { + debug_mode = 1; // Enable debug mode + fileName = PyUnicode_AsUTF8(arg); + if (fileName == NULL) { + PyErr_SetString(PyExc_TypeError, "file name must be a valid string"); + } + // Open the file and do debugging + FILE* log_file = fopen(fileName, "w"); + if (log_file == NULL) { + PyErr_SetString(PyExc_IOError, "Failed to open the log file"); + } + fclose(log_file); + } else { + PyErr_SetString(PyExc_TypeError, "argument must be a boolean or a string"); + } +} + /*!# ibm_db.createdb * * ===Description @@ -2263,6 +2940,10 @@ static int _python_ibm_db_dropdb(conn_handle *conn_res, PyObject *dbNameObj, int */ PyObject *ibm_db_createdb(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry createdb()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; PyObject *dbNameObj = NULL; PyObject *codesetObj = NULL; @@ -2270,16 +2951,27 @@ PyObject *ibm_db_createdb(PyObject *self, PyObject *args) int rc = -1; if ( !PyArg_ParseTuple( args, "OO|OO", &py_conn_res, &dbNameObj, &codesetObj, &modeObj ) ) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; } + + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, dbNameObj=%p, codesetObj=%p, modeObj=%p", + py_conn_res, dbNameObj, codesetObj, modeObj); + LogMsg(DEBUG, messageStr, fileName); + if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } rc = _python_ibm_db_createdb((conn_handle *)py_conn_res, dbNameObj, codesetObj, modeObj, 0); if ( rc == 0 ) { + LogMsg(INFO, "Database created successfully", fileName); + LogMsg(INFO, "exit createdb()", fileName); Py_RETURN_TRUE; } else { + LogMsg(ERROR, "Failed to create database", fileName); + LogMsg(INFO, "exit createdb()", fileName); return NULL; } } @@ -2304,21 +2996,33 @@ PyObject *ibm_db_createdb(PyObject *self, PyObject *args) */ PyObject *ibm_db_dropdb(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry dropdb()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; PyObject *dbNameObj = NULL; int rc = -1; if ( !PyArg_ParseTuple( args, "OO", &py_conn_res, &dbNameObj ) ) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, dbNameObj=%p", py_conn_res, dbNameObj); + LogMsg(DEBUG, messageStr, fileName); if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } rc = _python_ibm_db_dropdb( (conn_handle *)py_conn_res, dbNameObj, 0 ); if ( rc == 0 ) { + LogMsg(INFO, "Database droped successfully", fileName); + LogMsg(INFO, "exit dropdb()", fileName); Py_RETURN_TRUE; } else { + LogMsg(ERROR, "Failed to drop database", fileName); + LogMsg(INFO, "exit dropdb()", fileName); return NULL; } } @@ -2351,6 +3055,10 @@ PyObject *ibm_db_dropdb(PyObject *self, PyObject *args) */ PyObject *ibm_db_recreatedb(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry recreatedb()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; PyObject *dbNameObj = NULL; PyObject *codesetObj = NULL; @@ -2358,21 +3066,42 @@ PyObject *ibm_db_recreatedb(PyObject *self, PyObject *args) int rc = -1; if ( !PyArg_ParseTuple( args, "OO|OO", &py_conn_res, &dbNameObj, &codesetObj, &modeObj ) ) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, dbNameObj=%p, codesetObj=%p, modeObj=%p", (void *)py_conn_res, (void *)dbNameObj, (void *)codesetObj, (void *)modeObj); + LogMsg(DEBUG, messageStr, fileName); if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Calling _python_ibm_db_dropdb with parameters: conn_handle=%p, dbNameObj=%p, recreate=1", + (void *)py_conn_res, (void *)dbNameObj); + LogMsg(DEBUG, messageStr, fileName); rc = _python_ibm_db_dropdb((conn_handle *)py_conn_res, dbNameObj, 1 ); + snprintf(messageStr, sizeof(messageStr), "_python_ibm_db_dropdb returned: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc != 0 ) { + LogMsg(ERROR, "Failed to drop the database", fileName); + LogMsg(INFO, "exit recreatedb()", fileName); return NULL; + } else { + LogMsg(DEBUG, "Database dropped successfully", fileName); } - + snprintf(messageStr, sizeof(messageStr), "Calling _python_ibm_db_createdb with parameters: conn_handle=%p, dbNameObj=%p, codesetObj=%p, modeObj=%p, createNX=0", + (void *)py_conn_res, (void *)dbNameObj, (void *)codesetObj, (void *)modeObj); + LogMsg(DEBUG, messageStr, fileName); rc = _python_ibm_db_createdb((conn_handle *)py_conn_res, dbNameObj, codesetObj, modeObj, 0); + snprintf(messageStr, sizeof(messageStr), "_python_ibm_db_createdb returned: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == 0 ) { + LogMsg(DEBUG, "Database created successfully", fileName); + LogMsg(INFO, "exit recreatedb()", fileName); Py_RETURN_TRUE; } else { + LogMsg(ERROR, "Failed to create the database", fileName); + LogMsg(INFO, "exit recreatedb()", fileName); return NULL; } } @@ -2405,6 +3134,10 @@ PyObject *ibm_db_recreatedb(PyObject *self, PyObject *args) */ PyObject *ibm_db_createdbNX(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry createdbNX()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; PyObject *dbNameObj = NULL; PyObject *codesetObj = NULL; @@ -2412,16 +3145,27 @@ PyObject *ibm_db_createdbNX(PyObject *self, PyObject *args) int rc = -1; if ( !PyArg_ParseTuple( args, "OO|OO", &py_conn_res, &dbNameObj, &codesetObj, &modeObj ) ) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; } + + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, dbNameObj=%p, codesetObj=%p, modeObj=%p", + py_conn_res, dbNameObj, codesetObj, modeObj); + LogMsg(DEBUG, messageStr, fileName); + if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } rc = _python_ibm_db_createdb((conn_handle *)py_conn_res, dbNameObj, codesetObj, modeObj, 1); if ( rc == 0 ) { + LogMsg(INFO, "Database created successfully", fileName); + LogMsg(INFO, "exit createdbNX()", fileName); Py_RETURN_TRUE; } else { + LogMsg(ERROR, "Failed to create database", fileName); + LogMsg(INFO, "exit createdbNX()", fileName); return NULL; } } @@ -2462,6 +3206,10 @@ PyObject *ibm_db_createdbNX(PyObject *self, PyObject *args) */ static PyObject *ibm_db_autocommit(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry autocommt()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_autocommit = NULL; PyObject *py_conn_res = NULL; conn_handle *conn_res = NULL; @@ -2469,25 +3217,36 @@ static PyObject *ibm_db_autocommit(PyObject *self, PyObject *args) SQLINTEGER autocommit = -1; if (!PyArg_ParseTuple(args, "O|O", &py_conn_res, &py_autocommit)){ + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, py_autocommit=%p", (void *)py_conn_res, (void *)py_autocommit); + LogMsg(DEBUG, messageStr, fileName); + if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!NIL_P(py_autocommit)) { if (PyInt_Check(py_autocommit)) { - autocommit = (SQLINTEGER)PyInt_AsLong(py_autocommit); + autocommit = (SQLINTEGER)PyLong_AsLong(py_autocommit); + snprintf(messageStr, sizeof(messageStr), "Autocommit value parsed: %d", autocommit); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "Supplied parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); return NULL; } @@ -2495,6 +3254,8 @@ static PyObject *ibm_db_autocommit(PyObject *self, PyObject *args) /* If value in handle is different from value passed in */ if (PyTuple_Size(args) == 2) { if(autocommit != (conn_res->auto_commit)) { + snprintf(messageStr, sizeof(messageStr), "Updating autocommit setting. Current: %d, New: %d", conn_res->auto_commit, autocommit); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; #ifndef PASE rc = SQLSetConnectAttr((SQLHDBC)conn_res->hdbc, SQL_ATTR_AUTOCOMMIT, (SQLPOINTER) (autocommit == 0 ? SQL_AUTOCOMMIT_OFF : SQL_AUTOCOMMIT_ON), SQL_IS_INTEGER); @@ -2502,18 +3263,29 @@ static PyObject *ibm_db_autocommit(PyObject *self, PyObject *args) rc = SQLSetConnectAttr((SQLHDBC)conn_res->hdbc, SQL_ATTR_AUTOCOMMIT, (SQLPOINTER)&autocommit, SQL_IS_INTEGER); #endif Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLSetConnectAttr return code: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { + snprintf(messageStr, sizeof(messageStr), "An error occurred while setting autocommit. rc=%d", rc); + LogMsg(ERROR, messageStr, fileName); _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } conn_res->auto_commit = autocommit; + snprintf(messageStr, sizeof(messageStr), "Autocommit setting updated successfully. New value: %d", conn_res->auto_commit); + LogMsg(DEBUG, messageStr, fileName); } Py_INCREF(Py_True); + LogMsg(INFO, "exit autocommit()", fileName); return Py_True; } else { + snprintf(messageStr, sizeof(messageStr), "Returning current autocommit value: %d", conn_res->auto_commit); + LogMsg(INFO, messageStr, fileName); + LogMsg(INFO, "exit autocommit()", fileName); return PyInt_FromLong(conn_res->auto_commit); } } + LogMsg(INFO, "exit autocommit()", fileName); return NULL; } @@ -2521,6 +3293,15 @@ static PyObject *ibm_db_autocommit(PyObject *self, PyObject *args) */ static void _python_ibm_db_add_param_cache( stmt_handle *stmt_res, int param_no, PyObject *var_pyvalue, int param_type, int size, SQLSMALLINT data_type, SQLUINTEGER precision, SQLSMALLINT scale, SQLSMALLINT nullable ) { + LogMsg(INFO, "entry _python_ibm_db_add_param_cache()", fileName); + snprintf(messageStr, sizeof(messageStr), + "stmt_res=%p, param_no=%d, var_pyvalue=%p, param_type=%d, size=%d, data_type=%d, precision=%u, scale=%d, nullable=%d", + (void *)stmt_res, param_no, (void *)var_pyvalue, param_type, size, data_type, precision, scale, nullable); + LogMsg(DEBUG, messageStr, fileName); + snprintf(messageStr, sizeof(messageStr), + "Initial state: head_cache_list=%p, num_params=%d", + (void *)stmt_res->head_cache_list, stmt_res->num_params); + LogMsg(DEBUG, messageStr, fileName); param_node *tmp_curr = NULL, *prev = stmt_res->head_cache_list, *curr = stmt_res->head_cache_list; while ( (curr != NULL) && (curr->param_num < param_no) ) { @@ -2563,9 +3344,17 @@ static void _python_ibm_db_add_param_cache( stmt_handle *stmt_res, int param_no, /* Increment num params added */ stmt_res->num_params++; + snprintf(messageStr, sizeof(messageStr), + "Added new node: param_no=%d, tmp_curr=%p, head_cache_list=%p, num_params=%d", + param_no, (void *)tmp_curr, (void *)stmt_res->head_cache_list, stmt_res->num_params); + LogMsg(DEBUG, messageStr, fileName); } else { /* Both the nodes are for the same param no */ /* Replace Information */ + snprintf(messageStr, sizeof(messageStr), + "Replacing existing node: param_no=%d, curr=%p", + param_no, (void *)curr); + LogMsg(DEBUG, messageStr, fileName); curr->data_type = data_type; curr->param_size = precision; curr->nullable = nullable; @@ -2587,6 +3376,10 @@ static void _python_ibm_db_add_param_cache( stmt_handle *stmt_res, int param_no, } } + snprintf(messageStr, sizeof(messageStr), "Final state: head_cache_list=%p, num_params=%d", + (void *)stmt_res->head_cache_list, stmt_res->num_params); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit _python_ibm_db_add_param_cache()", fileName); } /* @@ -2595,13 +3388,22 @@ static void _python_ibm_db_add_param_cache( stmt_handle *stmt_res, int param_no, */ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_res, SQLUSMALLINT param_no, PyObject *var_pyvalue, long param_type, long data_type, long precision, long scale, long size) { + LogMsg(INFO, "entry _python_ibm_db_bind_param_helper()", fileName); SQLSMALLINT sql_data_type = 0; SQLUINTEGER sql_precision = 0; SQLSMALLINT sql_scale = 0; SQLSMALLINT sql_nullable = SQL_NO_NULLS; char error[DB2_MAX_ERR_MSG_LEN + 50]; int rc = 0; - + snprintf(messageStr, sizeof(messageStr), + "argc=%d, stmt_res=%p, param_no=%d, var_pyvalue=%p, param_type=%ld, data_type=%ld, precision=%ld, scale=%ld, size=%ld", + argc, (void *)stmt_res, param_no, (void *)var_pyvalue, param_type, data_type, precision, scale, size); + LogMsg(DEBUG, messageStr, fileName); + + snprintf(messageStr, sizeof(messageStr), + "Before SQLDescribeParam: sql_data_type=%d, sql_precision=%u, sql_scale=%d, sql_nullable=%d", + sql_data_type, sql_precision, sql_scale, sql_nullable); + LogMsg(DEBUG, messageStr, fileName); /* Check for Param options */ switch (argc) { /* if argc == 3, then the default value for param_type will be used */ @@ -2611,7 +3413,10 @@ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_re Py_BEGIN_ALLOW_THREADS; rc = SQLDescribeParam((SQLHSTMT)stmt_res->hstmt, (SQLUSMALLINT)param_no, &sql_data_type, &sql_precision, &sql_scale, &sql_nullable); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLDescribeParam called with parameters hstmt=%p, param_no=%d, and returned: rc=%d, sql_data_type=%d, sql_precision=%u, sql_scale=%d, sql_nullable=%d", + (void *)stmt_res->hstmt, param_no, rc, sql_data_type, sql_precision, sql_scale, sql_nullable); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO || rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, @@ -2621,6 +3426,7 @@ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_re if ( rc == SQL_ERROR ) { sprintf(error, "Describe Param Failed: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } @@ -2637,7 +3443,10 @@ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_re (SQLUSMALLINT)param_no, &sql_data_type, &sql_precision, &sql_scale, &sql_nullable); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLDescribeParam called with parameters hstmt=%p, param_no=%d and returned: rc=%d, sql_data_type=%d, sql_precision=%u, sql_scale=%d, sql_nullable=%d", + (void *)stmt_res->hstmt, param_no, rc, sql_data_type, sql_precision, sql_scale, sql_nullable); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO || rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, @@ -2647,6 +3456,7 @@ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_re if ( rc == SQL_ERROR ) { sprintf(error, "Describe Param Failed: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } @@ -2663,7 +3473,10 @@ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_re (SQLUSMALLINT)param_no, &sql_data_type, &sql_precision, &sql_scale, &sql_nullable); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLDescribeParam called with parameters hstmt=%p, param_no=%d and returned: rc=%d, sql_data_type=%d, sql_precision=%u, sql_scale=%d, sql_nullable=%d", + (void *)stmt_res->hstmt, param_no, rc, sql_data_type, sql_precision, sql_scale, sql_nullable); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO || rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, @@ -2673,6 +3486,7 @@ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_re if ( rc == SQL_ERROR ) { sprintf(error, "Describe Param Failed: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } @@ -2690,7 +3504,10 @@ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_re (SQLUSMALLINT)param_no, &sql_data_type, &sql_precision, &sql_scale, &sql_nullable); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLDescribeParam called with: hstmt=%p, param_no=%d; returned: rc=%d, sql_data_type=%d, sql_precision=%u, sql_scale=%d, sql_nullable=%d", + (void *)stmt_res->hstmt, param_no, rc, sql_data_type, sql_precision, sql_scale, sql_nullable); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO || rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, @@ -2700,6 +3517,7 @@ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_re if ( rc == SQL_ERROR ) { sprintf(error, "Describe Param Failed: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } @@ -2724,6 +3542,10 @@ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_re * CLI call because this might cause problems on other platforms * such as AIX */ + snprintf(messageStr, sizeof(messageStr), + "Before adding to cache: param_no=%d, var_pyvalue=%p, param_type=%ld, size=%ld, sql_data_type=%d, sql_precision=%u, sql_scale=%d, sql_nullable=%d", + param_no, (void *)var_pyvalue, param_type, size, sql_data_type, sql_precision, sql_scale, sql_nullable); + LogMsg(DEBUG, messageStr, fileName); sql_data_type = (SQLSMALLINT)data_type; sql_precision = (SQLUINTEGER)precision; sql_scale = (SQLSMALLINT)scale; @@ -2731,17 +3553,24 @@ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_re param_type, size, sql_data_type, sql_precision, sql_scale, sql_nullable ); + snprintf(messageStr, sizeof(messageStr), + "Added to cache: param_no=%d, var_pyvalue=%p, param_type=%ld, size=%ld, sql_data_type=%d, sql_precision=%u, sql_scale=%d, sql_nullable=%d", + param_no, (void *)var_pyvalue, param_type, size, sql_data_type, sql_precision, sql_scale, sql_nullable); + LogMsg(DEBUG, messageStr, fileName); break; default: /* WRONG_PARAM_COUNT; */ + LogMsg(ERROR, "Invalid argc value", fileName); + LogMsg(INFO, "exit _python_ibm_db_bind_param_helper()", fileName); return NULL; } /* end Switch */ /* We bind data with DB2 CLI in ibm_db.execute() */ /* This will save network flow if we need to override params in it */ - + LogMsg(DEBUG, "return value=Py_True", fileName); + LogMsg(INFO, "exit _python_ibm_db_bind_param_helper()", fileName); Py_INCREF(Py_True); return Py_True; } @@ -2806,6 +3635,10 @@ static PyObject *_python_ibm_db_bind_param_helper(int argc, stmt_handle *stmt_re */ static PyObject *ibm_db_bind_param(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry bind_param()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *var_pyvalue = NULL; PyObject *py_param_type = NULL; PyObject *py_data_type = NULL; @@ -2828,14 +3661,20 @@ static PyObject *ibm_db_bind_param(PyObject *self, PyObject *args) &var_pyvalue, &py_param_type, &py_data_type, &py_precision, &py_scale, &py_size)) { - + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, py_param_no=%p, var_pyvalue=%p, py_param_type=%p, py_data_type=%p, py_precision=%p, py_scale=%p, py_size=%p", + py_stmt_res, py_param_no, var_pyvalue, py_param_type, py_data_type, py_precision, py_scale, py_size); + LogMsg(DEBUG, messageStr, fileName); + if (!NIL_P(py_param_no)) { if (PyInt_Check(py_param_no)) { - param_no = (SQLUSMALLINT) PyInt_AsLong(py_param_no); + param_no = (SQLUSMALLINT) PyLong_AsLong(py_param_no); + LogMsg(DEBUG, "Parameter number set", fileName); } else { + LogMsg(ERROR, "Invalid parameter number", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } @@ -2843,43 +3682,57 @@ static PyObject *ibm_db_bind_param(PyObject *self, PyObject *args) if (py_param_type != NULL && py_param_type != Py_None && TYPE(py_param_type) == PYTHON_FIXNUM) { param_type = PyInt_AS_LONG(py_param_type); + LogMsg(DEBUG, "Parameter type set", fileName); } if (py_data_type != NULL && py_data_type != Py_None && TYPE(py_data_type) == PYTHON_FIXNUM) { data_type = PyInt_AS_LONG(py_data_type); + LogMsg(DEBUG, "Data type set", fileName); } if (py_precision != NULL && py_precision != Py_None && TYPE(py_precision) == PYTHON_FIXNUM) { precision = PyInt_AS_LONG(py_precision); + LogMsg(DEBUG, "Precision set", fileName); } if (py_scale != NULL && py_scale != Py_None && TYPE(py_scale) == PYTHON_FIXNUM) { scale = PyInt_AS_LONG(py_scale); + LogMsg(DEBUG, "Scale set", fileName); } if (py_size != NULL && py_size != Py_None && TYPE(py_size) == PYTHON_FIXNUM) { size = PyInt_AS_LONG(py_size); + LogMsg(DEBUG, "Size set", fileName); } + snprintf(messageStr, sizeof(messageStr), "Final values: param_no=%d, param_type=%ld, data_type=%ld, precision=%ld, scale=%ld, size=%ld", + param_no, param_type, data_type, precision, scale, size); + LogMsg(DEBUG, messageStr, fileName); + if (!NIL_P(py_stmt_res)) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } + LogMsg(INFO, "Calling and returning _python_ibm_db_bind_param_helper", fileName); + LogMsg(INFO, "exit bind_param()", fileName); return _python_ibm_db_bind_param_helper(PyTuple_Size(args), stmt_res, param_no, var_pyvalue, param_type, data_type, precision, scale, size); } else { + LogMsg(ERROR, "Supplied parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } } - /*!# ibm_db.close * * ===Description @@ -2903,19 +3756,31 @@ static PyObject *ibm_db_bind_param(PyObject *self, PyObject *args) */ static PyObject *ibm_db_close(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry close()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; conn_handle *conn_res = NULL; int rc; - if (!PyArg_ParseTuple(args, "O", &py_conn_res)) + if (!PyArg_ParseTuple(args, "O", &py_conn_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p", py_conn_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } /* Check to see if it's a persistent connection; @@ -2923,6 +3788,7 @@ static PyObject *ibm_db_close(PyObject *self, PyObject *args) */ if (!conn_res->handle_active) { + LogMsg(EXCEPTION, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); return NULL; } @@ -2936,6 +3802,8 @@ static PyObject *ibm_db_close(PyObject *self, PyObject *args) rc = SQLEndTran(SQL_HANDLE_DBC, (SQLHDBC)conn_res->hdbc, SQL_ROLLBACK); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQL rollback returned: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -2945,6 +3813,8 @@ static PyObject *ibm_db_close(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; rc = SQLDisconnect((SQLHDBC)conn_res->hdbc); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQL disconnect returned: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO || rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors( conn_res->hdbc, @@ -2958,7 +3828,8 @@ static PyObject *ibm_db_close(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; rc = SQLFreeHandle(SQL_HANDLE_DBC, conn_res->hdbc); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQL free handle (DBC) returned: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO || rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors( conn_res->hdbc, @@ -2971,12 +3842,16 @@ static PyObject *ibm_db_close(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; rc = SQLFreeHandle(SQL_HANDLE_ENV, conn_res->henv); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQL free handle (ENV) returned: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); return NULL; } Py_BEGIN_ALLOW_THREADS; rc = SQLFreeHandle(SQL_HANDLE_ENV, conn_res->henv); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQL free handle (ENV) returned: rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO || rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors( conn_res->henv, @@ -2990,15 +3865,21 @@ static PyObject *ibm_db_close(PyObject *self, PyObject *args) conn_res->handle_active = 0; Py_INCREF(Py_True); + LogMsg(INFO, "exit close()", fileName); return Py_True; } else if ( conn_res->flag_pconnect ) { /* Do we need to call FreeStmt or something to close cursors? */ + LogMsg(INFO, "Persistent connection detected; no action required", fileName); Py_INCREF(Py_True); + LogMsg(INFO, "exit close()", fileName); return Py_True; } else { + LogMsg(INFO, "exit close()", fileName); return NULL; } } else { + LogMsg(INFO, "No connection object provided", fileName); + LogMsg(INFO, "exit close()", fileName); return NULL; } } @@ -3051,6 +3932,10 @@ static PyObject *ibm_db_close(PyObject *self, PyObject *args) */ static PyObject *ibm_db_column_privileges(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry column_privileges()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); SQLWCHAR *qualifier = NULL; SQLWCHAR *owner = NULL; SQLWCHAR *table_name = NULL; @@ -3066,14 +3951,23 @@ static PyObject *ibm_db_column_privileges(PyObject *self, PyObject *args) int isNewBuffer; if (!PyArg_ParseTuple(args, "O|OOOO", &py_conn_res, &py_qualifier, &py_owner, - &py_table_name, &py_column_name)) + &py_table_name, &py_column_name)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, py_qualifier=%p, py_owner=%p, py_table_name=%p, py_column_name=%p", + py_conn_res, py_qualifier, py_owner, py_table_name, py_column_name); + LogMsg(DEBUG, messageStr, fileName); if (py_qualifier != NULL && py_qualifier != Py_None) { if (PyString_Check(py_qualifier) || PyUnicode_Check(py_qualifier)){ py_qualifier = PyUnicode_FromObject(py_qualifier); + snprintf(messageStr, sizeof(messageStr), "Converted py_qualifier to Unicode: %s", PyUnicode_AsUTF8(py_qualifier)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Qualifier must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "qualifier must be a string or unicode"); return NULL; } @@ -3082,8 +3976,11 @@ static PyObject *ibm_db_column_privileges(PyObject *self, PyObject *args) if (py_owner != NULL && py_owner != Py_None) { if (PyString_Check(py_owner) || PyUnicode_Check(py_owner)){ py_owner = PyUnicode_FromObject(py_owner); + snprintf(messageStr, sizeof(messageStr), "Converted py_owner to Unicode: %s", PyUnicode_AsUTF8(py_owner)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Owner must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "owner must be a string or unicode"); Py_XDECREF(py_qualifier); return NULL; @@ -3093,8 +3990,11 @@ static PyObject *ibm_db_column_privileges(PyObject *self, PyObject *args) if (py_table_name != NULL && py_table_name != Py_None) { if (PyString_Check(py_table_name) || PyUnicode_Check(py_table_name)){ py_table_name = PyUnicode_FromObject(py_table_name); + snprintf(messageStr, sizeof(messageStr), "Converted py_table_name to Unicode: %s", PyUnicode_AsUTF8(py_table_name)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Table name must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "table_name must be a string or unicode"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -3105,8 +4005,11 @@ static PyObject *ibm_db_column_privileges(PyObject *self, PyObject *args) if (py_column_name != NULL && py_column_name != Py_None) { if (PyString_Check(py_column_name) || PyUnicode_Check(py_table_name)){ py_column_name = PyUnicode_FromObject(py_column_name); + snprintf(messageStr, sizeof(messageStr), "Converted py_column_name to Unicode: %s", PyUnicode_AsUTF8(py_column_name)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Column name must be a string", fileName); PyErr_SetString(PyExc_Exception, "column_name must be a string"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -3117,13 +4020,17 @@ static PyObject *ibm_db_column_privileges(PyObject *self, PyObject *args) if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valie. conn_res=%p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -3136,9 +4043,12 @@ static PyObject *ibm_db_column_privileges(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, conn_res->hdbc, &(stmt_res->hstmt)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLAllocHandle(SQL_HANDLE_STMT) rc=%d, stmt_res->hstmt=%p", rc, (void *)stmt_res->hstmt); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); + LogMsg(ERROR, "SQLAllocHandle failed", fileName); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); @@ -3153,12 +4063,22 @@ static PyObject *ibm_db_column_privileges(PyObject *self, PyObject *args) if (py_table_name && py_table_name != Py_None ) table_name = getUnicodeDataAsSQLWCHAR(py_table_name, &isNewBuffer); + snprintf(messageStr, sizeof(messageStr), "Calling SQLColumnPrivilegesW: qualifier=%s, owner=%s, table_name=%s, column_name=%s", + qualifier ? (char *)qualifier : "NULL", + owner ? (char *)owner : "NULL", + table_name ? (char *)table_name : "NULL", + column_name ? (char *)column_name : "NULL"); + LogMsg(DEBUG, messageStr, fileName); + Py_BEGIN_ALLOW_THREADS; rc = SQLColumnPrivilegesW((SQLHSTMT)stmt_res->hstmt, qualifier, SQL_NTS, owner, SQL_NTS, table_name, SQL_NTS, column_name, SQL_NTS); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLColumnPrivilegesW rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); + if (isNewBuffer) { if(qualifier) PyMem_Del(qualifier); if(owner) PyMem_Del(owner); @@ -3168,6 +4088,7 @@ static PyObject *ibm_db_column_privileges(PyObject *self, PyObject *args) if (rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); + LogMsg(ERROR, "SQLColumnPrivilegesW failed", fileName); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); @@ -3179,14 +4100,15 @@ static PyObject *ibm_db_column_privileges(PyObject *self, PyObject *args) Py_XDECREF(py_owner); Py_XDECREF(py_table_name); Py_XDECREF(py_column_name); - + LogMsg(INFO, "exit column_privileges()", fileName); return (PyObject *)stmt_res; } else { + LogMsg(ERROR, "Connection resource is NULL or invalid", fileName); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); Py_XDECREF(py_column_name); - + LogMsg(INFO, "exit column_privileges()", fileName); Py_RETURN_FALSE; } } @@ -3253,6 +4175,10 @@ static PyObject *ibm_db_column_privileges(PyObject *self, PyObject *args) */ static PyObject *ibm_db_columns(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry columns()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); SQLWCHAR *qualifier = NULL; SQLWCHAR *owner = NULL; SQLWCHAR *table_name = NULL; @@ -3268,14 +4194,23 @@ static PyObject *ibm_db_columns(PyObject *self, PyObject *args) int isNewBuffer; if (!PyArg_ParseTuple(args, "O|OOOO", &py_conn_res, &py_qualifier, &py_owner, - &py_table_name, &py_column_name)) + &py_table_name, &py_column_name)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + + snprintf(messageStr, sizeof(messageStr), + "Parsed values: py_conn_res=%p, py_qualifier=%p, py_owner=%p, py_table_name=%p, py_column_name=%p", + py_conn_res, py_qualifier, py_owner, py_table_name, py_column_name); + LogMsg(DEBUG, messageStr, fileName); if (py_qualifier != NULL && py_qualifier != Py_None) { if (PyString_Check(py_qualifier) || PyUnicode_Check(py_qualifier)){ py_qualifier = PyUnicode_FromObject(py_qualifier); + LogMsg(DEBUG, "py_qualifier converted to Unicode", fileName); } else { + LogMsg(EXCEPTION, "qualifier must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "qualifier must be a string or unicode"); return NULL; } @@ -3284,8 +4219,10 @@ static PyObject *ibm_db_columns(PyObject *self, PyObject *args) if (py_owner != NULL && py_owner != Py_None) { if (PyString_Check(py_owner) || PyUnicode_Check(py_owner)){ py_owner = PyUnicode_FromObject(py_owner); + LogMsg(DEBUG, "py_owner converted to Unicode", fileName); } else { + LogMsg(EXCEPTION, "owner must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "owner must be a string or unicode"); Py_XDECREF(py_qualifier); return NULL; @@ -3295,8 +4232,10 @@ static PyObject *ibm_db_columns(PyObject *self, PyObject *args) if (py_table_name != NULL && py_table_name != Py_None) { if (PyString_Check(py_table_name) || PyUnicode_Check(py_table_name)){ py_table_name = PyUnicode_FromObject(py_table_name); + LogMsg(DEBUG, "py_table_name converted to Unicode", fileName); } else { + LogMsg(EXCEPTION, "table_name must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "table_name must be a string or unicode"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -3307,8 +4246,10 @@ static PyObject *ibm_db_columns(PyObject *self, PyObject *args) if (py_column_name != NULL && py_column_name != Py_None) { if (PyString_Check(py_column_name) || PyUnicode_Check(py_table_name)){ py_column_name = PyUnicode_FromObject(py_column_name); + LogMsg(DEBUG, "py_column_name converted to Unicode", fileName); } else { + LogMsg(EXCEPTION, "column_name must be a string", fileName); PyErr_SetString(PyExc_Exception, "column_name must be a string"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -3319,13 +4260,17 @@ static PyObject *ibm_db_columns(PyObject *self, PyObject *args) if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle: %p, handle_active=%d", conn_res, conn_res->handle_active); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -3335,13 +4280,18 @@ static PyObject *ibm_db_columns(PyObject *self, PyObject *args) } stmt_res = _ibm_db_new_stmt_struct(conn_res); + snprintf(messageStr, sizeof(messageStr), "Statement handle created: %p", stmt_res); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, conn_res->hdbc, &(stmt_res->hstmt)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLAllocHandle returned rc=%d, hstmt=%p", rc, stmt_res->hstmt); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); + LogMsg(ERROR, "SQLAllocHandle failed", fileName); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); @@ -3359,11 +4309,19 @@ static PyObject *ibm_db_columns(PyObject *self, PyObject *args) if (py_column_name && py_column_name != Py_None ) column_name = getUnicodeDataAsSQLWCHAR(py_column_name, &isNewBuffer); + snprintf(messageStr, sizeof(messageStr), + "SQL buffers: qualifier=%p, owner=%p, table_name=%p, column_name=%p, isNewBuffer=%d", + qualifier, owner, table_name, column_name, isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); + Py_BEGIN_ALLOW_THREADS; rc = SQLColumnsW((SQLHSTMT)stmt_res->hstmt, qualifier, SQL_NTS, owner,SQL_NTS, table_name, SQL_NTS, column_name, SQL_NTS); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLColumnsW returned rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); + if (isNewBuffer) { if(qualifier) PyMem_Del(qualifier); if(owner) PyMem_Del(owner); @@ -3374,6 +4332,7 @@ static PyObject *ibm_db_columns(PyObject *self, PyObject *args) if (rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); + LogMsg(ERROR, "SQLColumnsW failed", fileName); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); @@ -3387,13 +4346,15 @@ static PyObject *ibm_db_columns(PyObject *self, PyObject *args) Py_XDECREF(py_column_name); Py_INCREF(Py_None); + LogMsg(INFO, "exit columns()", fileName); return (PyObject *)stmt_res; } else { + LogMsg(INFO, "No connection provided or connection is NIL", fileName); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); Py_XDECREF(py_column_name); - + LogMsg(INFO, "exit columns()", fileName); Py_RETURN_FALSE; } } @@ -3468,6 +4429,10 @@ static PyObject *ibm_db_columns(PyObject *self, PyObject *args) */ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry foreign_keys()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); SQLWCHAR *pk_qualifier = NULL; SQLWCHAR *pk_owner = NULL; SQLWCHAR *pk_table_name = NULL; @@ -3488,14 +4453,19 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) if (!PyArg_ParseTuple(args, "OOOO|OOO", &py_conn_res, &py_pk_qualifier, &py_pk_owner, &py_pk_table_name, &py_fk_qualifier, - &py_fk_owner, &py_fk_table_name)) + &py_fk_owner, &py_fk_table_name)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, pk_qualifier=%s, pk_owner=%s, pk_table_name=%s, fk_qualifier=%s, fk_owner=%s, fk_table_name=%s", + (void *)py_conn_res, (void *)py_pk_qualifier, (void *)py_pk_owner, (void *)py_pk_table_name, (void *)py_fk_qualifier, (void *)py_fk_owner, (void *)py_fk_table_name); + LogMsg(DEBUG, messageStr, fileName); if (py_pk_qualifier != NULL && py_pk_qualifier != Py_None) { if (PyString_Check(py_pk_qualifier) || PyUnicode_Check(py_pk_qualifier)){ py_pk_qualifier = PyUnicode_FromObject(py_pk_qualifier); } else { + LogMsg(EXCEPTION, "qualifier for table containing primary key must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "qualifier for table containing primary key must be a string or unicode"); return NULL; @@ -3507,6 +4477,7 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) py_pk_owner = PyUnicode_FromObject(py_pk_owner); } else { + LogMsg(EXCEPTION, "owner of table containing primary key must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "owner of table containing primary key must be a string or unicode"); Py_XDECREF(py_pk_qualifier); @@ -3519,6 +4490,7 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) py_pk_table_name = PyUnicode_FromObject(py_pk_table_name); } else { + LogMsg(EXCEPTION, "name of the table that contains primary key must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "name of the table that contains primary key must be a string or unicode"); Py_XDECREF(py_pk_qualifier); @@ -3532,6 +4504,7 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) py_fk_qualifier = PyUnicode_FromObject(py_fk_qualifier); } else { + LogMsg(EXCEPTION, "qualifier for table containing the foreign key must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "qualifier for table containing the foreign key must be a string or unicode"); Py_XDECREF(py_pk_qualifier); @@ -3546,6 +4519,7 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) py_fk_owner = PyUnicode_FromObject(py_fk_owner); } else { + LogMsg(EXCEPTION, "owner of table containing the foreign key must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "owner of table containing the foreign key must be a string or unicode"); Py_XDECREF(py_pk_qualifier); @@ -3561,6 +4535,7 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) py_fk_table_name = PyUnicode_FromObject(py_fk_table_name); } else { + LogMsg(EXCEPTION, "name of the table that contains foreign key must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "name of the table that contains foreign key must be a string or unicode"); Py_XDECREF(py_pk_qualifier); @@ -3574,13 +4549,17 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. stmt_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); Py_XDECREF(py_pk_qualifier); Py_XDECREF(py_pk_owner); @@ -3596,7 +4575,9 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, conn_res->hdbc, &(stmt_res->hstmt)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLAllocHandle called with SQL_HANDLE_STMT, conn_res->hdbc=%p, &(stmt_res->hstmt)=%p and returned rc=%d", + (void *)conn_res->hdbc, (void *)stmt_res->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -3622,13 +4603,17 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) fk_owner = getUnicodeDataAsSQLWCHAR(py_fk_owner, &isNewBuffer); if(py_fk_table_name && py_fk_table_name != Py_None) fk_table_name = getUnicodeDataAsSQLWCHAR(py_fk_table_name, &isNewBuffer); - + snprintf(messageStr, sizeof(messageStr), "Calling SQLForeignKeysW with parameters: pk_qualifier=%p, pk_owner=%p, pk_table_name=%p, fk_qualifier=%p, fk_owner=%p, fk_table_name=%p", + (void *)pk_qualifier, (void *)pk_owner, (void *)pk_table_name, + (void *)fk_qualifier, (void *)fk_owner, (void *)fk_table_name); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLForeignKeysW((SQLHSTMT)stmt_res->hstmt, pk_qualifier, SQL_NTS, pk_owner, SQL_NTS, pk_table_name, SQL_NTS, fk_qualifier, SQL_NTS, fk_owner, SQL_NTS, fk_table_name, SQL_NTS); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLForeignKeysW returned rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); if (isNewBuffer) { if(pk_qualifier) PyMem_Del(pk_qualifier); if(pk_owner) PyMem_Del(pk_owner); @@ -3656,6 +4641,7 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) Py_XDECREF(py_fk_qualifier); Py_XDECREF(py_fk_owner); Py_XDECREF(py_fk_table_name); + LogMsg(INFO, "exit foreign_keys()", fileName); return (PyObject *)stmt_res; } else { @@ -3665,6 +4651,7 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) Py_XDECREF(py_fk_qualifier); Py_XDECREF(py_fk_owner); Py_XDECREF(py_fk_table_name); + LogMsg(INFO, "exit foreign_keys()", fileName); Py_RETURN_FALSE; } } @@ -3710,6 +4697,10 @@ static PyObject *ibm_db_foreign_keys(PyObject *self, PyObject *args) */ static PyObject *ibm_db_primary_keys(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry primary_keys()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); SQLWCHAR *qualifier = NULL; SQLWCHAR *owner = NULL; SQLWCHAR *table_name = NULL; @@ -3723,14 +4714,20 @@ static PyObject *ibm_db_primary_keys(PyObject *self, PyObject *args) int isNewBuffer; if (!PyArg_ParseTuple(args, "OOOO", &py_conn_res, &py_qualifier, &py_owner, - &py_table_name)) + &py_table_name)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, py_qualifier=%p, py_owner=%p, py_table_name=%p",py_conn_res, py_qualifier, py_owner, py_table_name); + LogMsg(INFO, messageStr, fileName); if (py_qualifier != NULL && py_qualifier != Py_None) { if (PyString_Check(py_qualifier) || PyUnicode_Check(py_qualifier)){ py_qualifier = PyUnicode_FromObject(py_qualifier); + snprintf(messageStr, sizeof(messageStr), "Converted qualifier to Unicode: %s", PyUnicode_AsUTF8(py_qualifier)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "qualifier must be as string or unicode", fileName); PyErr_SetString(PyExc_Exception, "qualifier must be a string or unicode"); return NULL; } @@ -3739,8 +4736,11 @@ static PyObject *ibm_db_primary_keys(PyObject *self, PyObject *args) if (py_owner != NULL && py_owner != Py_None) { if (PyString_Check(py_owner) || PyUnicode_Check(py_owner)){ py_owner = PyUnicode_FromObject(py_owner); + snprintf(messageStr, sizeof(messageStr), "Converted owner to Unicode: %s", PyUnicode_AsUTF8(py_owner)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "owner must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "owner must be a string or unicode"); Py_XDECREF(py_qualifier); return NULL; @@ -3750,8 +4750,11 @@ static PyObject *ibm_db_primary_keys(PyObject *self, PyObject *args) if (py_table_name != NULL && py_table_name != Py_None) { if (PyString_Check(py_table_name) || PyUnicode_Check(py_table_name)){ py_table_name = PyUnicode_FromObject(py_table_name); + snprintf(messageStr, sizeof(messageStr), "Converted table_name to Unicode: %s", PyUnicode_AsUTF8(py_table_name)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "table_name must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "table_name must be a string or unicode"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -3761,6 +4764,7 @@ static PyObject *ibm_db_primary_keys(PyObject *self, PyObject *args) if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { @@ -3768,6 +4772,7 @@ static PyObject *ibm_db_primary_keys(PyObject *self, PyObject *args) } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -3776,10 +4781,16 @@ static PyObject *ibm_db_primary_keys(PyObject *self, PyObject *args) } stmt_res = _ibm_db_new_stmt_struct(conn_res); + snprintf(messageStr, sizeof(messageStr), "New statement structure created. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, conn_res->hdbc, &(stmt_res->hstmt)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), + "SQLAllocHandle called with parameters SQL_HANDLE_STMT=%d, conn_res->hdbc=%p, stmt_res->hstmt=%p and returned rc=%d", + SQL_HANDLE_STMT, (void *)conn_res->hdbc, (void *)stmt_res->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -3800,6 +4811,10 @@ static PyObject *ibm_db_primary_keys(PyObject *self, PyObject *args) rc = SQLPrimaryKeysW((SQLHSTMT)stmt_res->hstmt, qualifier, SQL_NTS, owner, SQL_NTS, table_name, SQL_NTS); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), + "SQLPrimaryKeysW called with parameters SQLHSTMT=%p, qualifier=%p, SQL_NTS, owner=%p, SQL_NTS, table_name=%p, SQL_NTS and returned rc=%d", + (SQLHSTMT)stmt_res->hstmt, (void *)qualifier, (void *)owner, (void *)table_name, rc); + LogMsg(DEBUG, messageStr, fileName); if (isNewBuffer) { if(qualifier) PyMem_Del(qualifier); @@ -3819,14 +4834,15 @@ static PyObject *ibm_db_primary_keys(PyObject *self, PyObject *args) Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); - + LogMsg(INFO, "exit primary_keys()", fileName); return (PyObject *)stmt_res; } else { + LogMsg(ERROR, "Supplied connection object parameter is NULL", fileName); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); - + LogMsg(INFO, "exit primary_keys()", fileName); Py_RETURN_FALSE; } } @@ -3909,6 +4925,10 @@ static PyObject *ibm_db_primary_keys(PyObject *self, PyObject *args) */ static PyObject *ibm_db_procedure_columns(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry procedure_columns()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); SQLWCHAR *qualifier = NULL; SQLWCHAR *owner = NULL; SQLWCHAR *proc_name = NULL; @@ -3924,14 +4944,20 @@ static PyObject *ibm_db_procedure_columns(PyObject *self, PyObject *args) int isNewBuffer; if (!PyArg_ParseTuple(args, "O|OOOO", &py_conn_res, &py_qualifier, &py_owner, - &py_proc_name, &py_column_name)) + &py_proc_name, &py_column_name)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, py_qualifier=%p, py_owner=%p, py_proc_name=%p, py_column_name=%p",py_conn_res, py_qualifier, py_owner, py_proc_name, py_column_name); + LogMsg(DEBUG, messageStr, fileName); if (py_qualifier != NULL && py_qualifier != Py_None) { if (PyString_Check(py_qualifier) || PyUnicode_Check(py_qualifier)){ py_qualifier = PyUnicode_FromObject(py_qualifier); + snprintf(messageStr, sizeof(messageStr), "Converted qualifier to Unicode: %s", PyUnicode_AsUTF8(py_qualifier)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "qualifier must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "qualifier must be a string or unicode"); return NULL; } @@ -3940,8 +4966,11 @@ static PyObject *ibm_db_procedure_columns(PyObject *self, PyObject *args) if (py_owner != NULL && py_owner != Py_None) { if (PyString_Check(py_owner) || PyUnicode_Check(py_owner)){ py_owner = PyUnicode_FromObject(py_owner); + snprintf(messageStr, sizeof(messageStr), "Converted owner to Unicode: %s", PyUnicode_AsUTF8(py_owner)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "owner must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "owner must be a string or unicode"); Py_XDECREF(py_qualifier); return NULL; @@ -3951,9 +4980,12 @@ static PyObject *ibm_db_procedure_columns(PyObject *self, PyObject *args) if (py_proc_name != NULL && py_proc_name != Py_None) { if (PyString_Check(py_proc_name) || PyUnicode_Check(py_proc_name)){ py_proc_name = PyUnicode_FromObject(py_proc_name); + snprintf(messageStr, sizeof(messageStr), "Converted proc_name to Unicode: %s", PyUnicode_AsUTF8(py_proc_name)); + LogMsg(DEBUG, messageStr, fileName); } else { - PyErr_SetString(PyExc_Exception, "table_name must be a string or unicode"); + LogMsg(EXCEPTION, "proc_name must be a string or unicode", fileName); + PyErr_SetString(PyExc_Exception, "proc_name must be a string or unicode"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); return NULL; @@ -3963,8 +4995,11 @@ static PyObject *ibm_db_procedure_columns(PyObject *self, PyObject *args) if (py_column_name != NULL && py_column_name != Py_None) { if (PyString_Check(py_column_name) || PyUnicode_Check(py_column_name)){ py_column_name = PyUnicode_FromObject(py_column_name); + snprintf(messageStr, sizeof(messageStr), "Converted column_name to Unicode: %s", PyUnicode_AsUTF8(py_column_name)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "column_name must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "column_name must be a string or unicode"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -3975,13 +5010,17 @@ static PyObject *ibm_db_procedure_columns(PyObject *self, PyObject *args) if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -3991,10 +5030,16 @@ static PyObject *ibm_db_procedure_columns(PyObject *self, PyObject *args) } stmt_res = _ibm_db_new_stmt_struct(conn_res); + snprintf(messageStr, sizeof(messageStr), "New statement structure created. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, conn_res->hdbc, &(stmt_res->hstmt)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), + "SQLAllocHandle called with parameters SQL_HANDLE_STMT=%d, conn_res->hdbc=%p, stmt_res->hstmt=%p and returned rc=%d", + SQL_HANDLE_STMT, (void *)conn_res->hdbc, (void *)stmt_res->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -4019,7 +5064,10 @@ static PyObject *ibm_db_procedure_columns(PyObject *self, PyObject *args) owner, SQL_NTS, proc_name, SQL_NTS, column_name, SQL_NTS); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLProcedureColumnsW called with parameters SQLHSTMT=%p, qualifier=%p, owner=%p, proc_name=%p, column_name=%p and returned rc=%d", + (SQLHSTMT)stmt_res->hstmt, (void *)qualifier, (void *)owner, (void *)proc_name, (void *)column_name, rc); + LogMsg(DEBUG, messageStr, fileName); if (isNewBuffer) { if(qualifier) PyMem_Del(qualifier); if(owner) PyMem_Del(owner); @@ -4041,14 +5089,15 @@ static PyObject *ibm_db_procedure_columns(PyObject *self, PyObject *args) Py_XDECREF(py_owner); Py_XDECREF(py_proc_name); Py_XDECREF(py_column_name); - + LogMsg(INFO, "exit procedure_columns()", fileName); return (PyObject *)stmt_res; } else { + LogMsg(ERROR, "Supplied connection object parameter is NULL", fileName); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_proc_name); Py_XDECREF(py_column_name); - + LogMsg(INFO, "exit procedure_columns()", fileName); Py_RETURN_FALSE; } } @@ -4099,6 +5148,10 @@ static PyObject *ibm_db_procedure_columns(PyObject *self, PyObject *args) */ static PyObject *ibm_db_procedures(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry procedures()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); SQLWCHAR *qualifier = NULL; SQLWCHAR *owner = NULL; SQLWCHAR *proc_name = NULL; @@ -4111,15 +5164,20 @@ static PyObject *ibm_db_procedures(PyObject *self, PyObject *args) PyObject *py_proc_name = NULL; int isNewBuffer; - if (!PyArg_ParseTuple(args, "OOOO", &py_conn_res, &py_qualifier, &py_owner, - &py_proc_name)) + if (!PyArg_ParseTuple(args, "OOOO", &py_conn_res, &py_qualifier, &py_owner, &py_proc_name)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, py_qualifier=%p, py_owner=%p, py_proc_name=%p",py_conn_res, py_qualifier, py_owner, py_proc_name); + LogMsg(DEBUG, messageStr, fileName); if (py_qualifier != NULL && py_qualifier != Py_None) { if (PyString_Check(py_qualifier) || PyUnicode_Check(py_qualifier)){ py_qualifier = PyUnicode_FromObject(py_qualifier); + snprintf(messageStr, sizeof(messageStr), "Converted qualifier to Unicode: %s", PyUnicode_AsUTF8(py_qualifier)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "qualifier must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "qualifier must be a string or unicode"); return NULL; } @@ -4128,8 +5186,11 @@ static PyObject *ibm_db_procedures(PyObject *self, PyObject *args) if (py_owner != NULL && py_owner != Py_None) { if (PyString_Check(py_owner) || PyUnicode_Check(py_owner)){ py_owner = PyUnicode_FromObject(py_owner); + snprintf(messageStr, sizeof(messageStr), "Converted owner to Unicode: %s", PyUnicode_AsUTF8(py_owner)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "owner must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "owner must be a string or unicode"); Py_XDECREF(py_qualifier); return NULL; @@ -4139,9 +5200,12 @@ static PyObject *ibm_db_procedures(PyObject *self, PyObject *args) if (py_proc_name != NULL && py_proc_name != Py_None) { if (PyString_Check(py_proc_name) || PyUnicode_Check(py_proc_name)){ py_proc_name = PyUnicode_FromObject(py_proc_name); + snprintf(messageStr, sizeof(messageStr), "Converted proc_name to Unicode: %s", PyUnicode_AsUTF8(py_proc_name)); + LogMsg(DEBUG, messageStr, fileName); } else { - PyErr_SetString(PyExc_Exception, "table_name must be a string or unicode"); + LogMsg(EXCEPTION, "proc_name must be a string or unicode", fileName); + PyErr_SetString(PyExc_Exception, "proc_name must be a string or unicode"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); return NULL; @@ -4151,13 +5215,17 @@ static PyObject *ibm_db_procedures(PyObject *self, PyObject *args) if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -4166,10 +5234,16 @@ static PyObject *ibm_db_procedures(PyObject *self, PyObject *args) } stmt_res = _ibm_db_new_stmt_struct(conn_res); + snprintf(messageStr, sizeof(messageStr), "New statement structure created. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, conn_res->hdbc, &(stmt_res->hstmt)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), + "SQLAllocHandle called with parameters SQL_HANDLE_STMT=%d, conn_res->hdbc=%p, stmt_res->hstmt=%p and returned rc=%d", + SQL_HANDLE_STMT, (void *)conn_res->hdbc, (void *)stmt_res->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -4190,7 +5264,10 @@ static PyObject *ibm_db_procedures(PyObject *self, PyObject *args) rc = SQLProceduresW((SQLHSTMT)stmt_res->hstmt, qualifier, SQL_NTS, owner, SQL_NTS, proc_name, SQL_NTS); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLProceduresW called with parameters SQLHSTMT=%p, qualifier=%p, owner=%p, proc_name=%p and returned rc=%d", + (SQLHSTMT)stmt_res->hstmt, (void *)qualifier, (void *)owner, (void *)proc_name, rc); + LogMsg(DEBUG, messageStr, fileName); if (isNewBuffer) { if(qualifier) PyMem_Del(qualifier); if(owner) PyMem_Del(owner); @@ -4209,12 +5286,14 @@ static PyObject *ibm_db_procedures(PyObject *self, PyObject *args) Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_proc_name); + LogMsg(INFO, "exit procedures()", fileName); return (PyObject *)stmt_res; } else { + LogMsg(ERROR, "Supplied connection object parameter is NULL", fileName); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_proc_name); - + LogMsg(INFO, "exit procedures()", fileName); Py_RETURN_FALSE; } } @@ -4296,6 +5375,10 @@ static PyObject *ibm_db_procedures(PyObject *self, PyObject *args) */ static PyObject *ibm_db_special_columns(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry special_columns()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); SQLWCHAR *qualifier = NULL; SQLWCHAR *owner = NULL; SQLWCHAR *table_name = NULL; @@ -4310,14 +5393,19 @@ static PyObject *ibm_db_special_columns(PyObject *self, PyObject *args) PyObject *py_table_name = NULL; int isNewBuffer; - if (!PyArg_ParseTuple(args, "OOOOO", &py_conn_res, &py_qualifier, &py_owner, - &py_table_name, &py_scope)) + if (!PyArg_ParseTuple(args, "OOOOO", &py_conn_res, &py_qualifier, &py_owner, &py_table_name, &py_scope)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, py_qualifier=%p, py_owner=%p, py_table_name=%p, py_scope=%p", py_conn_res, py_qualifier, py_owner, py_table_name, py_scope); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_scope)) { if (PyInt_Check(py_scope)) { - scope = (int) PyInt_AsLong(py_scope); + scope = (int) PyLong_AsLong(py_scope); + snprintf(messageStr, sizeof(messageStr), "Scope value: %d", scope); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "Supplied scope parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } @@ -4325,8 +5413,11 @@ static PyObject *ibm_db_special_columns(PyObject *self, PyObject *args) if (py_qualifier != NULL && py_qualifier != Py_None) { if (PyString_Check(py_qualifier) || PyUnicode_Check(py_qualifier)){ py_qualifier = PyUnicode_FromObject(py_qualifier); + snprintf(messageStr, sizeof(messageStr), "Converted qualifier to Unicode: %s", PyUnicode_AsUTF8(py_qualifier)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "qualifier must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "qualifier must be a string or unicode"); return NULL; } @@ -4335,8 +5426,11 @@ static PyObject *ibm_db_special_columns(PyObject *self, PyObject *args) if (py_owner != NULL && py_owner != Py_None) { if (PyString_Check(py_owner) || PyUnicode_Check(py_owner)){ py_owner = PyUnicode_FromObject(py_owner); + snprintf(messageStr, sizeof(messageStr), "Converted owner to Unicode: %s", PyUnicode_AsUTF8(py_owner)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "owner must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "owner must be a string or unicode"); Py_XDECREF(py_qualifier); return NULL; @@ -4346,8 +5440,11 @@ static PyObject *ibm_db_special_columns(PyObject *self, PyObject *args) if (py_table_name != NULL && py_table_name != Py_None) { if (PyString_Check(py_table_name) || PyUnicode_Check(py_table_name)){ py_table_name = PyUnicode_FromObject(py_table_name); + snprintf(messageStr, sizeof(messageStr), "Converted table_name to Unicode: %s", PyUnicode_AsUTF8(py_table_name)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "table_name must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "table_name must be a string or unicode"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -4357,13 +5454,17 @@ static PyObject *ibm_db_special_columns(PyObject *self, PyObject *args) if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -4372,10 +5473,14 @@ static PyObject *ibm_db_special_columns(PyObject *self, PyObject *args) } stmt_res = _ibm_db_new_stmt_struct(conn_res); - + snprintf(messageStr, sizeof(messageStr), "New statement structure created. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, conn_res->hdbc, &(stmt_res->hstmt)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLAllocHandle with parameters SQL_HANDLE_STMT=%d, hdbc=%p, hstmt=%p and returned rc=%d", + SQL_HANDLE_STMT, (void *)conn_res->hdbc, (void *)&(stmt_res->hstmt), rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -4397,7 +5502,10 @@ static PyObject *ibm_db_special_columns(PyObject *self, PyObject *args) qualifier, SQL_NTS, owner, SQL_NTS, table_name, SQL_NTS, scope, SQL_NULLABLE); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "Called SQLSpecialColumnsW with parameters: " + "hstmt=%p, scope=%d, qualifier=%p, owner=%p, table_name=%p, nullable=%d and returned rc=%d", + (void *)stmt_res->hstmt, scope, (void *)qualifier, (void *)owner, (void *)table_name, SQL_NULLABLE, rc); + LogMsg(DEBUG, messageStr, fileName); if (isNewBuffer) { if(qualifier) PyMem_Del(qualifier); if(owner) PyMem_Del(owner); @@ -4416,13 +5524,13 @@ static PyObject *ibm_db_special_columns(PyObject *self, PyObject *args) Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); - + LogMsg(INFO, "exit special_columns()", fileName); return (PyObject *)stmt_res; } else { Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); - + LogMsg(INFO, "exit special_columns()", fileName); Py_RETURN_FALSE; } @@ -4514,6 +5622,10 @@ static PyObject *ibm_db_special_columns(PyObject *self, PyObject *args) */ static PyObject *ibm_db_statistics(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry statistics()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); SQLWCHAR *qualifier = NULL; SQLWCHAR *owner = NULL; SQLWCHAR *table_name = NULL; @@ -4529,15 +5641,20 @@ static PyObject *ibm_db_statistics(PyObject *self, PyObject *args) PyObject *py_unique = NULL; int isNewBuffer; - if (!PyArg_ParseTuple(args, "OOOOO", &py_conn_res, &py_qualifier, &py_owner, - &py_table_name, &py_unique)) + if (!PyArg_ParseTuple(args, "OOOOO", &py_conn_res, &py_qualifier, &py_owner, &py_table_name, &py_unique)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, py_qualifier=%p, py_owner=%p, py_table_name=%p, py_unique=%p", py_conn_res, py_qualifier, py_owner, py_table_name, py_unique); + LogMsg(DEBUG, messageStr, fileName); if (py_qualifier != NULL && py_qualifier != Py_None) { if (PyString_Check(py_qualifier) || PyUnicode_Check(py_qualifier)){ py_qualifier = PyUnicode_FromObject(py_qualifier); + snprintf(messageStr, sizeof(messageStr), "Converted qualifier to Unicode: %s", PyUnicode_AsUTF8(py_qualifier)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "qualifier must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "qualifier must be a string or unicode"); return NULL; } @@ -4546,8 +5663,11 @@ static PyObject *ibm_db_statistics(PyObject *self, PyObject *args) if (py_owner != NULL && py_owner != Py_None) { if (PyString_Check(py_owner) || PyUnicode_Check(py_owner)){ py_owner = PyUnicode_FromObject(py_owner); + snprintf(messageStr, sizeof(messageStr), "Converted owner to Unicode: %s", PyUnicode_AsUTF8(py_owner)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "owner must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "owner must be a string or unicode"); Py_XDECREF(py_qualifier); return NULL; @@ -4557,8 +5677,11 @@ static PyObject *ibm_db_statistics(PyObject *self, PyObject *args) if (py_table_name != NULL && py_table_name != Py_None) { if (PyString_Check(py_table_name) || PyUnicode_Check(py_table_name)){ py_table_name = PyUnicode_FromObject(py_table_name); + snprintf(messageStr, sizeof(messageStr), "Converted table_name to Unicode: %s", PyUnicode_AsUTF8(py_table_name)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "table_name must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "table_name must be a string or unicode"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -4572,8 +5695,11 @@ static PyObject *ibm_db_statistics(PyObject *self, PyObject *args) unique = 1; else unique = 0; + snprintf(messageStr, sizeof(messageStr), "Converted unique to integer: %d", unique); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "unique must be a boolean", fileName); PyErr_SetString(PyExc_Exception, "unique must be a boolean"); return NULL; } @@ -4581,13 +5707,17 @@ static PyObject *ibm_db_statistics(PyObject *self, PyObject *args) if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -4596,11 +5726,17 @@ static PyObject *ibm_db_statistics(PyObject *self, PyObject *args) } stmt_res = _ibm_db_new_stmt_struct(conn_res); + snprintf(messageStr, sizeof(messageStr), "New statement structure created. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); sql_unique = unique; Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, conn_res->hdbc, &(stmt_res->hstmt)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), + "SQLAllocHandle called with parameters SQL_HANDLE_STMT=%d, conn_res->hdbc=%p, stmt_res->hstmt=%p and returned rc=%d", + SQL_HANDLE_STMT, (void *)conn_res->hdbc, (void *)stmt_res->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -4621,7 +5757,10 @@ static PyObject *ibm_db_statistics(PyObject *self, PyObject *args) rc = SQLStatisticsW((SQLHSTMT)stmt_res->hstmt, qualifier, SQL_NTS, owner, SQL_NTS, table_name, SQL_NTS, sql_unique, SQL_QUICK); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLStatisticsW called with parameters: stmt_res->hstmt=%p, qualifier=%p, owner=%p, table_name=%p, sql_unique=%d, SQL_QUICK=%d and returned rc=%d", + (void *)stmt_res->hstmt, (void *)qualifier, (void *)owner, (void *)table_name, sql_unique, SQL_QUICK, rc); + LogMsg(DEBUG, messageStr, fileName); if (isNewBuffer) { if(qualifier) PyMem_Del(qualifier); if(owner) PyMem_Del(owner); @@ -4640,13 +5779,14 @@ static PyObject *ibm_db_statistics(PyObject *self, PyObject *args) Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); - + LogMsg(INFO, "exit statistics()", fileName); return (PyObject *)stmt_res; } else { + LogMsg(ERROR, "Supplied connection object parameter is NULL", fileName); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); - + LogMsg(INFO, "exit statistics()", fileName); Py_RETURN_FALSE; } } @@ -4697,6 +5837,10 @@ static PyObject *ibm_db_statistics(PyObject *self, PyObject *args) */ static PyObject *ibm_db_table_privileges(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry table_privileges()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); SQLWCHAR *qualifier = NULL; SQLWCHAR *owner = NULL; SQLWCHAR *table_name = NULL; @@ -4709,15 +5853,20 @@ static PyObject *ibm_db_table_privileges(PyObject *self, PyObject *args) PyObject *py_table_name = NULL; int isNewBuffer; - if (!PyArg_ParseTuple(args, "O|OOO", &py_conn_res, &py_qualifier, &py_owner, - &py_table_name)) + if (!PyArg_ParseTuple(args, "O|OOO", &py_conn_res, &py_qualifier, &py_owner, &py_table_name)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, py_qualifier=%p, py_owner=%p, py_table_name=%p",py_conn_res, py_qualifier, py_owner, py_table_name); + LogMsg(DEBUG, messageStr, fileName); if (py_qualifier != NULL && py_qualifier != Py_None) { if (PyString_Check(py_qualifier) || PyUnicode_Check(py_qualifier)){ py_qualifier = PyUnicode_FromObject(py_qualifier); + snprintf(messageStr, sizeof(messageStr), "Converted qualifier to Unicode: %s", PyUnicode_AsUTF8(py_qualifier)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "qualifier must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "qualifier must be a string or unicode"); return NULL; } @@ -4726,8 +5875,11 @@ static PyObject *ibm_db_table_privileges(PyObject *self, PyObject *args) if (py_owner != NULL && py_owner != Py_None) { if (PyString_Check(py_owner) || PyUnicode_Check(py_owner)){ py_owner = PyUnicode_FromObject(py_owner); + snprintf(messageStr, sizeof(messageStr), "Converted owner to Unicode: %s", PyUnicode_AsUTF8(py_owner)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "owner must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "owner must be a string or unicode"); Py_XDECREF(py_qualifier); return NULL; @@ -4737,8 +5889,11 @@ static PyObject *ibm_db_table_privileges(PyObject *self, PyObject *args) if (py_table_name != NULL && py_table_name != Py_None) { if (PyString_Check(py_table_name) || PyUnicode_Check(py_table_name)){ py_table_name = PyUnicode_FromObject(py_table_name); + snprintf(messageStr, sizeof(messageStr), "Converted table_name to Unicode: %s", PyUnicode_AsUTF8(py_table_name)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "table_name must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "table_name must be a string or unicode"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -4748,13 +5903,17 @@ static PyObject *ibm_db_table_privileges(PyObject *self, PyObject *args) if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -4763,15 +5922,22 @@ static PyObject *ibm_db_table_privileges(PyObject *self, PyObject *args) } if (!conn_res) { + LogMsg(ERROR, "Connectin Resource cannot be found", fileName); PyErr_SetString(PyExc_Exception,"Connection Resource cannot be found"); Py_RETURN_FALSE; } stmt_res = _ibm_db_new_stmt_struct(conn_res); + snprintf(messageStr, sizeof(messageStr), "New statement structure created. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, conn_res->hdbc, &(stmt_res->hstmt)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), + "SQLAllocHandle called with parameters SQL_HANDLE_STMT=%d, conn_res->hdbc=%p, stmt_res->hstmt=%p and returned rc=%d", + SQL_HANDLE_STMT, (void *)conn_res->hdbc, (void *)stmt_res->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -4792,7 +5958,10 @@ static PyObject *ibm_db_table_privileges(PyObject *self, PyObject *args) rc = SQLTablePrivilegesW((SQLHSTMT)stmt_res->hstmt, qualifier, SQL_NTS, owner, SQL_NTS, table_name, SQL_NTS); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLTablePrivilegesW called with parameters SQLHSTMT=%p, qualifier=%p, owner=%p, table_name=%p and returned rc=%d", + (SQLHSTMT)stmt_res->hstmt, (void *)qualifier, (void *)owner, (void *)table_name, rc); + LogMsg(DEBUG, messageStr, fileName); if (isNewBuffer) { if(qualifier) PyMem_Del(qualifier); if(owner) PyMem_Del(owner); @@ -4811,13 +5980,13 @@ static PyObject *ibm_db_table_privileges(PyObject *self, PyObject *args) Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); - + LogMsg(INFO, "exit table_privileges()", fileName); return (PyObject *)stmt_res; } else { Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); - + LogMsg(INFO, "exit table_privileges()", fileName); Py_RETURN_FALSE; } } @@ -4870,6 +6039,10 @@ static PyObject *ibm_db_table_privileges(PyObject *self, PyObject *args) */ static PyObject *ibm_db_tables(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry tables()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); SQLWCHAR *qualifier = NULL; SQLWCHAR *owner = NULL; SQLWCHAR *table_name = NULL; @@ -4884,15 +6057,20 @@ static PyObject *ibm_db_tables(PyObject *self, PyObject *args) int rc; int isNewBuffer; - if (!PyArg_ParseTuple(args, "O|OOOO", &py_conn_res, &py_qualifier, &py_owner, - &py_table_name, &py_table_type)) + if (!PyArg_ParseTuple(args, "O|OOOO", &py_conn_res, &py_qualifier, &py_owner, &py_table_name, &py_table_type)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, py_qualifier=%p, py_owner=%p, py_table_name=%p, py_table_type=%p",py_conn_res, py_qualifier, py_owner, py_table_name, py_table_type); + LogMsg(DEBUG, messageStr, fileName); if (py_qualifier != NULL && py_qualifier != Py_None) { if (PyString_Check(py_qualifier) || PyUnicode_Check(py_qualifier)){ py_qualifier = PyUnicode_FromObject(py_qualifier); + snprintf(messageStr, sizeof(messageStr), "Converted qualifier to Unicode: %s", PyUnicode_AsUTF8(py_qualifier)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "qualifier must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "qualifier must be a string or unicode"); return NULL; } @@ -4901,8 +6079,11 @@ static PyObject *ibm_db_tables(PyObject *self, PyObject *args) if (py_owner != NULL && py_owner != Py_None) { if (PyString_Check(py_owner) || PyUnicode_Check(py_owner)){ py_owner = PyUnicode_FromObject(py_owner); + snprintf(messageStr, sizeof(messageStr), "Converted owner to Unicode: %s", PyUnicode_AsUTF8(py_owner)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "owner must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "owner must be a string or unicode"); Py_XDECREF(py_qualifier); return NULL; @@ -4912,8 +6093,11 @@ static PyObject *ibm_db_tables(PyObject *self, PyObject *args) if (py_table_name != NULL && py_table_name != Py_None) { if (PyString_Check(py_table_name) || PyUnicode_Check(py_table_name)){ py_table_name = PyUnicode_FromObject(py_table_name); + snprintf(messageStr, sizeof(messageStr), "Converted table_name to Unicode: %s", PyUnicode_AsUTF8(py_table_name)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "table_name must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "table_name must be a string or unicode"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -4924,8 +6108,11 @@ static PyObject *ibm_db_tables(PyObject *self, PyObject *args) if (py_table_type != NULL && py_table_type != Py_None) { if (PyString_Check(py_table_type) || PyUnicode_Check(py_table_type)){ py_table_type = PyUnicode_FromObject(py_table_type); + snprintf(messageStr, sizeof(messageStr), "Converted table_type to Unicode: %s", PyUnicode_AsUTF8(py_table_type)); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "table type must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "table type must be a string or unicode"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -4936,13 +6123,17 @@ static PyObject *ibm_db_tables(PyObject *self, PyObject *args) if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); @@ -4952,10 +6143,15 @@ static PyObject *ibm_db_tables(PyObject *self, PyObject *args) } stmt_res = _ibm_db_new_stmt_struct(conn_res); - + snprintf(messageStr, sizeof(messageStr), "New statement structure created. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, conn_res->hdbc, &(stmt_res->hstmt)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), + "SQLAllocHandle called with parameters SQL_HANDLE_STMT=%d, conn_res->hdbc=%p, stmt_res->hstmt=%p and returned rc=%d", + SQL_HANDLE_STMT, (void *)conn_res->hdbc, (void *)stmt_res->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -4979,7 +6175,10 @@ static PyObject *ibm_db_tables(PyObject *self, PyObject *args) rc = SQLTablesW((SQLHSTMT)stmt_res->hstmt, qualifier, SQL_NTS, owner, SQL_NTS, table_name, SQL_NTS, table_type, SQL_NTS); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLTablesW called with parameters SQLHSTMT=%p, qualifier=%p, owner=%p, table_name=%p, table_type=%p and returned rc=%d", + (SQLHSTMT)stmt_res->hstmt, (void *)qualifier, (void *)owner, (void *)table_name, (void *)table_type, rc); + LogMsg(DEBUG, messageStr, fileName); if (isNewBuffer) { if(qualifier) PyMem_Del(qualifier); if(owner) PyMem_Del(owner); @@ -5001,14 +6200,14 @@ static PyObject *ibm_db_tables(PyObject *self, PyObject *args) Py_XDECREF(py_owner); Py_XDECREF(py_table_name); Py_XDECREF(py_table_type); - + LogMsg(INFO, "exit tables()", fileName); return (PyObject *)stmt_res; } else { Py_XDECREF(py_qualifier); Py_XDECREF(py_owner); Py_XDECREF(py_table_name); Py_XDECREF(py_table_type); - + LogMsg(INFO, "exit tables()", fileName); Py_RETURN_FALSE; } } @@ -5040,22 +6239,35 @@ static PyObject *ibm_db_tables(PyObject *self, PyObject *args) */ static PyObject *ibm_db_commit(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry commit()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; conn_handle *conn_res; int rc; - if (!PyArg_ParseTuple(args, "O", &py_conn_res)) + if (!PyArg_ParseTuple(args, "O", &py_conn_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + + snprintf(messageStr, sizeof(messageStr), "Parsed arguments: py_conn_res: %p", (void *)py_conn_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(EXCEPTION, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); return NULL; } @@ -5064,17 +6276,25 @@ static PyObject *ibm_db_commit(PyObject *self, PyObject *args) rc = SQLEndTran(SQL_HANDLE_DBC, conn_res->hdbc, SQL_COMMIT); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLEndTran returned rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); + if ( rc == SQL_ERROR ) { + LogMsg(ERROR, "SQLEndTran failed", fileName); _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); Py_INCREF(Py_False); return Py_False; } else { + LogMsg(INFO, "Transaction committed successfully", fileName); Py_INCREF(Py_True); + LogMsg(INFO, "exit commit()", fileName); return Py_True; } } + LogMsg(INFO, "No connection object provided, returning False", fileName); Py_INCREF(Py_False); + LogMsg(INFO, "exit commit()", fileName); return Py_False; } @@ -5082,11 +6302,14 @@ static PyObject *ibm_db_commit(PyObject *self, PyObject *args) */ static int _python_ibm_db_do_prepare(SQLHANDLE hdbc, SQLWCHAR *stmt, int stmt_size, stmt_handle *stmt_res, PyObject *options) { + LogMsg(INFO, "entry _python_ibm_db_do_prepare()", fileName); int rc; /* alloc handle and return only if it errors */ Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, hdbc, &(stmt_res->hstmt)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLAllocHandle result: %d, stmt_res->hstmt: %p", rc, stmt_res->hstmt); + LogMsg(INFO, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -5095,6 +6318,7 @@ static int _python_ibm_db_do_prepare(SQLHANDLE hdbc, SQLWCHAR *stmt, int stmt_si /* get the string and its length */ if (NIL_P(stmt)) { + LogMsg(EXCEPTION, "Supplied statement parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied statement parameter is invalid"); return rc; @@ -5102,6 +6326,7 @@ static int _python_ibm_db_do_prepare(SQLHANDLE hdbc, SQLWCHAR *stmt, int stmt_si if ( rc < SQL_SUCCESS ) { _python_ibm_db_check_sql_errors(hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); + LogMsg(ERROR, "Statement prepare Failed", fileName); PyErr_SetString(PyExc_Exception, "Statement prepare Failed: "); return rc; } @@ -5109,10 +6334,12 @@ static int _python_ibm_db_do_prepare(SQLHANDLE hdbc, SQLWCHAR *stmt, int stmt_si if (!NIL_P(options)) { rc = _python_ibm_db_parse_options( options, SQL_HANDLE_STMT, stmt_res ); if ( rc == SQL_ERROR ) { + LogMsg(INFO, "exit _python_ibm_db_do_prepare()", fileName); return rc; } } - + snprintf(messageStr, sizeof(messageStr), "Preparing SQL statement: %ls, size: %d", stmt, stmt_size); + LogMsg(DEBUG, messageStr, fileName); /* Prepare the stmt. The cursor type requested has already been set in * _python_ibm_db_assign_options */ @@ -5121,9 +6348,15 @@ static int _python_ibm_db_do_prepare(SQLHANDLE hdbc, SQLWCHAR *stmt, int stmt_si #ifdef __MVS__ rc = SQLPrepareW((SQLHSTMT)stmt_res->hstmt, stmt, stmt_size*2); + snprintf(messageStr, sizeof(messageStr), "SQLPrepareW called with: hstmt=%p, stmt=%p, stmt_size=%d, and returned rc: %d", + (void *)stmt_res->hstmt, (void *)stmt, stmt_size*2, rc); + LogMsg(DEBUG, messageStr, fileName); #else rc = SQLPrepareW((SQLHSTMT)stmt_res->hstmt, stmt, stmt_size); + snprintf(messageStr, sizeof(messageStr), "SQLPrepareW called with: hstmt=%p, stmt=%p, stmt_size=%d, and returned rc: %d", + (void *)stmt_res->hstmt, (void *)stmt, stmt_size, rc); + LogMsg(DEBUG, messageStr, fileName); #endif Py_END_ALLOW_THREADS; @@ -5131,6 +6364,7 @@ static int _python_ibm_db_do_prepare(SQLHANDLE hdbc, SQLWCHAR *stmt, int stmt_si _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } + LogMsg(INFO, "exit _python_ibm_db_do_prepare()", fileName); return rc; } @@ -5186,6 +6420,10 @@ static int _python_ibm_db_do_prepare(SQLHANDLE hdbc, SQLWCHAR *stmt, int stmt_si */ static PyObject *ibm_db_exec(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry exec_immediate()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received argument: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *options = NULL; PyObject *py_conn_res = NULL; stmt_handle *stmt_res; @@ -5204,14 +6442,20 @@ static PyObject *ibm_db_exec(PyObject *self, PyObject *args) * After completing statement execution, it returns the statement resource */ - if (!PyArg_ParseTuple(args, "OO|O", &py_conn_res, &py_stmt, &options)) + if (!PyArg_ParseTuple(args, "OO|O", &py_conn_res, &py_stmt, &options)){ + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed arguments: py_conn_res: %p, py_stmt=%p, options=%p", (void *)py_conn_res, (void *)py_stmt, (void *)options); + LogMsg(DEBUG, messageStr, fileName); if (py_stmt != NULL && py_stmt != Py_None) { if (PyString_Check(py_stmt) || PyUnicode_Check(py_stmt)){ py_stmt = PyUnicode_FromObject(py_stmt); + snprintf(messageStr, sizeof(messageStr), "py_stmt converted to Unicode. py_stmt: %p", (void *)py_stmt); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(EXCEPTION, "statement must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "statement must be a string or unicode"); return NULL; } @@ -5219,13 +6463,17 @@ static PyObject *ibm_db_exec(PyObject *self, PyObject *args) if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(EXCEPTION, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "py_conn_res is valid. Converted to conn_handle. py_conn_res: %p", (void *)py_conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(EXCEPTION, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); Py_XDECREF(py_stmt); return NULL; @@ -5233,6 +6481,8 @@ static PyObject *ibm_db_exec(PyObject *self, PyObject *args) return_str = ALLOC_N(char, DB2_MAX_ERR_MSG_LEN); if ( return_str == NULL ) { + snprintf(messageStr, sizeof(messageStr), "Failed to allocate memory. Requested size: %d", DB2_MAX_ERR_MSG_LEN); + LogMsg(EXCEPTION, messageStr, fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); Py_XDECREF(py_stmt); return NULL; @@ -5243,15 +6493,20 @@ static PyObject *ibm_db_exec(PyObject *self, PyObject *args) _python_ibm_db_clear_stmt_err_cache(); stmt_res = _ibm_db_new_stmt_struct(conn_res); + snprintf(messageStr, sizeof(messageStr), "New statement structure allocated. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); /* Allocates the stmt handle */ /* returns the stat_handle back to the calling function */ Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, conn_res->hdbc, &(stmt_res->hstmt)); + snprintf(messageStr, sizeof(messageStr), "SQLAllocHandle result: rc = %d, stmt_res->hstmt: %p", rc, (void *)stmt_res->hstmt); + LogMsg(DEBUG, messageStr, fileName); Py_END_ALLOW_THREADS; if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); + LogMsg(ERROR, "SQLAllocHandle failed with SQL_ERROR", fileName); PyMem_Del(return_str); Py_XDECREF(py_stmt); return NULL; @@ -5259,22 +6514,30 @@ static PyObject *ibm_db_exec(PyObject *self, PyObject *args) if (!NIL_P(options)) { rc = _python_ibm_db_parse_options(options, SQL_HANDLE_STMT, stmt_res); + snprintf(messageStr, sizeof(messageStr), "Parsed options. rc = %d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { + LogMsg(ERROR, "Error parsing options", fileName); Py_XDECREF(py_stmt); return NULL; } } if (py_stmt != NULL && py_stmt != Py_None){ stmt = getUnicodeDataAsSQLWCHAR(py_stmt, &isNewBuffer); - } + snprintf(messageStr, sizeof(messageStr), "Converted py_stmt to SQLWCHAR. stmt: %p", (void *)stmt); + LogMsg(DEBUG, messageStr, fileName); + } Py_BEGIN_ALLOW_THREADS; rc = SQLExecDirectW((SQLHSTMT)stmt_res->hstmt, stmt, SQL_NTS); + snprintf(messageStr, sizeof(messageStr), "SQLExecDirectW result: rc = %d", rc); + LogMsg(DEBUG, messageStr, fileName); Py_END_ALLOW_THREADS; if ( rc < SQL_SUCCESS ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, -1, 1, return_str, DB2_ERRMSG, stmt_res->errormsg_recno_tracker); + LogMsg(ERROR, "SQLExecDirectW failed with SQL_ERROR", fileName); Py_BEGIN_ALLOW_THREADS; SQLFreeHandle( SQL_HANDLE_STMT, stmt_res->hstmt ); Py_END_ALLOW_THREADS; @@ -5289,6 +6552,7 @@ static PyObject *ibm_db_exec(PyObject *self, PyObject *args) } if ( rc == SQL_SUCCESS_WITH_INFO ) { + LogMsg(INFO, "SQLExecDirectW succeeded with warnings", fileName); _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, 1, 1, return_str, DB2_WARNMSG, stmt_res->errormsg_recno_tracker); @@ -5298,9 +6562,13 @@ static PyObject *ibm_db_exec(PyObject *self, PyObject *args) } PyMem_Del(return_str); Py_XDECREF(py_stmt); + snprintf(messageStr, sizeof(messageStr), "Statement execution successful. Returning stmt_res: %p", (void *)stmt_res); + LogMsg(INFO, messageStr, fileName); + LogMsg(INFO, "exit exec_immediate()", fileName); return (PyObject *)stmt_res; } Py_XDECREF(py_stmt); + LogMsg(INFO, "exit exec_immediate()", fileName); return NULL; } @@ -5325,19 +6593,29 @@ static PyObject *ibm_db_exec(PyObject *self, PyObject *args) */ static PyObject *ibm_db_free_result(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry free_result()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; stmt_handle *stmt_res; int rc = 0; - if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) + if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p", py_stmt_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_stmt_res)) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if ( stmt_res->hstmt ) { /* Free any cursors that might have been allocated in a previous call @@ -5346,6 +6624,9 @@ static PyObject *ibm_db_free_result(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; rc = SQLFreeStmt((SQLHSTMT)stmt_res->hstmt, SQL_CLOSE); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLFreeStmt called with parameters: stmt_res->hstmt=%p, SQL_CLOSE=%d and returned rc=%d", + (void *)stmt_res->hstmt, SQL_CLOSE, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, SQL_HANDLE_STMT, @@ -5358,10 +6639,12 @@ static PyObject *ibm_db_free_result(PyObject *self, PyObject *args) } _python_ibm_db_free_result_struct(stmt_res); } else { + LogMsg(EXCEPTION, "Supplied parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } Py_INCREF(Py_True); + LogMsg(INFO, "exit free_result()", fileName); return Py_True; } @@ -5371,6 +6654,7 @@ static PyObject *ibm_db_free_result(PyObject *self, PyObject *args) */ static PyObject *_python_ibm_db_prepare_helper(conn_handle *conn_res, PyObject *py_stmt, PyObject *options) { + LogMsg(INFO, "entry _python_ibm_db_prepare_helper()", fileName); stmt_handle *stmt_res; int rc; char error[DB2_MAX_ERR_MSG_LEN +50]; @@ -5379,21 +6663,35 @@ static PyObject *_python_ibm_db_prepare_helper(conn_handle *conn_res, PyObject * int isNewBuffer; if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); return NULL; } - + snprintf(messageStr, sizeof(messageStr), "Connection handle active: %d", conn_res->handle_active); + LogMsg(DEBUG, messageStr, fileName); + if (py_stmt != Py_None && PyUnicode_Check(py_stmt)) { + snprintf(messageStr, sizeof(messageStr), "Initial py_stmt: %s", py_stmt ? PyUnicode_AsUTF8(py_stmt) : "NULL"); + LogMsg(DEBUG, messageStr, fileName); + } + if (options != NULL && PyUnicode_Check(options)) { + snprintf(messageStr, sizeof(messageStr), "Options: %s", options ? PyUnicode_AsUTF8(options) : "NULL"); + LogMsg(DEBUG, messageStr, fileName); + } if (py_stmt != NULL && py_stmt != Py_None) { if (PyString_Check(py_stmt) || PyUnicode_Check(py_stmt)) { py_stmt = PyUnicode_FromObject(py_stmt); if (py_stmt != NULL && py_stmt != Py_None) { stmt_size = PyUnicode_GetLength(py_stmt); + snprintf(messageStr, sizeof(messageStr), "Converted py_stmt to Unicode, length: %d", stmt_size); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Error occure during processing of statement", fileName); PyErr_SetString(PyExc_Exception, "Error occure during processing of statement"); return NULL; } } else { + LogMsg(EXCEPTION, "statement must be a string or unicode", fileName); PyErr_SetString(PyExc_Exception, "statement must be a string or unicode"); return NULL; } @@ -5405,27 +6703,37 @@ static PyObject *_python_ibm_db_prepare_helper(conn_handle *conn_res, PyObject * /* Parsing will update options if needed */ stmt_res = _ibm_db_new_stmt_struct(conn_res); + snprintf(messageStr, sizeof(messageStr), "Initialized new stmt handle: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); /* Allocates the stmt handle */ /* Prepares the statement */ /* returns the stat_handle back to the calling function */ - if( py_stmt && py_stmt != Py_None) + if( py_stmt && py_stmt != Py_None) { stmt = getUnicodeDataAsSQLWCHAR(py_stmt, &isNewBuffer); + snprintf(messageStr, sizeof(messageStr), "Allocated stmt buffer: %p, isNewBuffer: %d", (void *)stmt, isNewBuffer); + LogMsg(DEBUG, messageStr, fileName); + } rc = _python_ibm_db_do_prepare(conn_res->hdbc, stmt, stmt_size, stmt_res, options); + snprintf(messageStr, sizeof(messageStr), "Prepared statement, return code: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if (isNewBuffer) { if(stmt) PyMem_Del(stmt); } if ( rc < SQL_SUCCESS ) { sprintf(error, "Statement Prepare Failed: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); Py_XDECREF(py_stmt); return NULL; } Py_XDECREF(py_stmt); + LogMsg(INFO, "exit _python_ibm_db_prepare_helper()", fileName); return (PyObject *)stmt_res; } + /*!# ibm_db.prepare * * ===Description @@ -5491,25 +6799,40 @@ static PyObject *_python_ibm_db_prepare_helper(conn_handle *conn_res, PyObject * */ static PyObject *ibm_db_prepare(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry prepare()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; PyObject *options = NULL; conn_handle *conn_res; PyObject *py_stmt = NULL; - if (!PyArg_ParseTuple(args, "OO|O", &py_conn_res, &py_stmt, &options)) + if (!PyArg_ParseTuple(args, "OO|O", &py_conn_res, &py_stmt, &options)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + + snprintf(messageStr, sizeof(messageStr), "Parsed arguments: py_conn_res: %p, py_stmt: %p, options: %p", + (void *)py_conn_res, (void *)py_stmt, (void *)options); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(EXCEPTION, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection object is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } + LogMsg(INFO, "Calling and returning _python_ibm_db_prepare_helper", fileName); + LogMsg(INFO, "exit prepare()", fileName); return _python_ibm_db_prepare_helper(conn_res, py_stmt, options); } - + LogMsg(INFO, "exit prepare()", fileName); return NULL; } @@ -5551,6 +6874,7 @@ static param_node* build_list( stmt_handle *stmt_res, int param_no, SQLSMALLINT */ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, PyObject *bind_data) { + LogMsg(INFO, "entry _python_ibm_db_bind_data()", fileName); int rc,i; SQLSMALLINT valueType = 0; SQLPOINTER paramValuePtr; @@ -5564,7 +6888,9 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py int param_length; int type = PYTHON_NIL; PyObject* item; - + snprintf(messageStr, sizeof(messageStr), "Parameters: stmt_res=%p, curr->param_type=%d, bind_data=%p", + (void*)stmt_res, curr->param_type, (void*)bind_data); + LogMsg(DEBUG, messageStr, fileName); /* Have to use SQLBindFileToParam if PARAM is type PARAM_FILE */ /*** Need to fix this***/ if ( curr->param_type == PARAM_FILE) { @@ -5574,10 +6900,12 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py if (PyUnicode_Check(bind_data)) { FileNameObj = PyUnicode_AsASCIIString(bind_data); if (FileNameObj == NULL) { + LogMsg(ERROR, "PyUnicode_AsASCIIString failed", fileName); return SQL_ERROR; } } } else { + LogMsg(ERROR, "bind_data is not a string type", fileName); return SQL_ERROR; } curr->bind_indicator = 0; @@ -5603,28 +6931,45 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py (SQLSMALLINT*)&(curr->ivalue), &(curr->file_options), (SQLSMALLINT) curr->ivalue, &(curr->bind_indicator)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "Called SQLBindFileToParam with parameters: hstmt=%p, param_num=%d, data_type=%d, svalue=%s, ivalue=%d, file_options=%p, ivalue_count=%d, bind_indicator=%p, and returned rc=%d", + (void*)stmt_res->hstmt, curr->param_num, curr->data_type, curr->svalue, curr->ivalue, (void*)&(curr->file_options), curr->ivalue, (void*)&(curr->bind_indicator), rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } return rc; + LogMsg(INFO, "exit _python_ibm_db_bind_data()", fileName); } type = TYPE(bind_data); + snprintf(messageStr, sizeof(messageStr), "Initial bind_data type: %d", type); + LogMsg(DEBUG, messageStr, fileName); if(type == PYTHON_LIST) { Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "Size of bind_data (list): %zd", n); + LogMsg(DEBUG, messageStr, fileName); for (i=0; idata_type == SQL_BIGINT || curr->data_type == SQL_DECIMAL )){ #if PY_MAJOR_VERSION >= 3 @@ -5635,12 +6980,16 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py { char *svalue = NULL; Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "PYTHON_LIST detected with size: %zd", n); + LogMsg(DEBUG, messageStr, fileName); curr->svalue = (char *)ALLOC_N(char, (MAX_PRECISION) * (n)); curr->bind_indicator_array = (SQLINTEGER *) ALLOC_N(SQLINTEGER, n); memset(curr->svalue , 0, MAX_PRECISION * n); for (i = 0; i < n; i++) { item = PyList_GetItem(bind_data, i); + snprintf(messageStr, sizeof(messageStr), "List index %d, item pointer: %p", i, (void*)item); + LogMsg(DEBUG, messageStr, fileName); if (TYPE(item) == PYTHON_NIL){ curr->bind_indicator_array[i] = SQL_NULL_DATA; }else { @@ -5654,6 +7003,9 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->ivalue = strlen(svalue); memcpy(curr->svalue + (i * MAX_PRECISION), svalue, curr->ivalue); svalue = NULL; + snprintf(messageStr, sizeof(messageStr), + "Processing list item index %d: svalue=%s, ivalue=%d", i, svalue, curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); curr->bind_indicator_array[i] = SQL_NTS; } } @@ -5663,7 +7015,9 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->param_type, SQL_C_CHAR, curr->data_type, MAX_PRECISION, curr->scale, curr->svalue, MAX_PRECISION, &curr->bind_indicator_array[0]); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with parameters: hstmt=%p, param_num=%d, param_type=%d, c_type=%d, data_type=%d, precision=%lu, scale=%d, svalue=%s, buffer_length=%lu, bind_indicator_array=%p and returned rc:%d", + (void*)stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_CHAR, curr->data_type, (unsigned long)MAX_PRECISION, curr->scale, curr->svalue, (unsigned long)MAX_PRECISION, (void*)&curr->bind_indicator_array[0], rc); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -5681,12 +7035,17 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->svalue = memcpy(PyMem_Malloc((sizeof(char))*(curr->ivalue+1)), curr->svalue, curr->ivalue); curr->svalue[curr->ivalue] = '\0'; curr->bind_indicator = curr->ivalue; - + snprintf(messageStr, sizeof(messageStr), + "Processing single value: svalue=%s, ivalue=%d, bind_indicator=%d", curr->svalue, curr->ivalue, curr->bind_indicator); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_CHAR, curr->data_type, curr->param_size, curr->scale, curr->svalue, curr->param_size, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with parameters: hstmt=%p, param_num=%d, param_type=%d, c_type=%d, data_type=%d, param_size=%lu, scale=%d, svalue=%s, buffer_length=%lu, bind_indicator=%p and returned rc=%d", + (void*)stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_CHAR, curr->data_type, (unsigned long)curr->param_size, curr->scale, curr->svalue, (unsigned long)curr->param_size, (void*)NULL, rc); + LogMsg(DEBUG, messageStr, fileName); } if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ){ @@ -5699,11 +7058,15 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py if(TYPE(bind_data) == PYTHON_LIST) { Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "PYTHON_LIST detected with size: %zd", n); + LogMsg(DEBUG, messageStr, fileName); curr->ivalueArray = (SQLINTEGER *)ALLOC_N(SQLINTEGER, n); curr->bind_indicator_array = (SQLINTEGER *) ALLOC_N(SQLINTEGER, n); for (i = 0; i < n; i++) { item = PyList_GetItem(bind_data, i); + snprintf(messageStr, sizeof(messageStr), "List index %d, item pointer: %p", i, (void*)item); + LogMsg(DEBUG, messageStr, fileName); if (TYPE(item) == PYTHON_NIL){ curr->ivalueArray[i] = NULL; curr->bind_indicator_array[i] = SQL_NULL_DATA; @@ -5718,18 +7081,25 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->param_type, SQL_C_LONG, curr->data_type, curr->param_size, curr->scale, curr->ivalueArray, 0, &curr->bind_indicator_array[0]); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with hstmt=%p, param_num=%d, param_type=%d, c_type=%d, data_type=%d, param_size=%lu, scale=%d, ivalueArray=%p, buffer_length=%lu, bind_indicator_array=%p, rc=%d", (void*)stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_LONG, curr->data_type, + (unsigned long)curr->param_size, curr->scale, (void*)curr->ivalueArray, (unsigned long)0, (void*)&curr->bind_indicator_array[0], rc); + LogMsg(DEBUG, messageStr, fileName); } else { curr->ivalue = (SQLINTEGER) PyLong_AsLong(bind_data); - + snprintf(messageStr, sizeof(messageStr), + "Processing single value: ivalue=%d", curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_LONG, curr->data_type, curr->param_size, curr->scale, &curr->ivalue, 0, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with parameters: hstmt=%p, param_num=%d, param_type=%d, c_type=%d, data_type=%d, param_size=%lu, scale=%d, ivalue=%d, buffer_length=%lu, bind_indicator=%p and returned rc=%d", (void*)stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_LONG, + curr->data_type, (unsigned long)curr->param_size, curr->scale, curr->ivalue, (unsigned long)0, (void*)NULL, rc); + LogMsg(DEBUG, messageStr, fileName); } - if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); @@ -5740,20 +7110,29 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py /* Convert BOOLEAN types to LONG for DB2 / Cloudscape */ case PYTHON_FALSE: + snprintf(messageStr, sizeof(messageStr), "Handling PYTHON_FALSE case with type=%d", type); + LogMsg(DEBUG, messageStr, fileName); if(TYPE(bind_data) == PYTHON_LIST) { Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "PYTHON_LIST detected with size: %zd", n); + LogMsg(DEBUG, messageStr, fileName); curr->ivalueArray = (SQLINTEGER *)ALLOC_N(SQLINTEGER, n); curr->bind_indicator_array = (SQLINTEGER *) ALLOC_N(SQLINTEGER, n); for (i = 0; i < n; i++) { item = PyList_GetItem(bind_data, i); + snprintf(messageStr, sizeof(messageStr), "List index %d, item pointer: %p", i, (void*)item); + LogMsg(DEBUG, messageStr, fileName); if (TYPE(item) == PYTHON_NIL){ curr->ivalueArray[i] = NULL; curr->bind_indicator_array[i] = SQL_NULL_DATA; } else { curr->ivalueArray[i] = PyLong_AsLong(item); curr->bind_indicator_array[i] = SQL_NTS; + snprintf(messageStr, sizeof(messageStr), "Processed list item index %d: ivalueArray[%d]=%d, bind_indicator_array[%d]=%d", + i, i, curr->ivalueArray[i], i, curr->bind_indicator_array[i]); + LogMsg(DEBUG, messageStr, fileName); } } @@ -5762,16 +7141,23 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->param_type, SQL_C_LONG, curr->data_type, curr->param_size, curr->scale, curr->ivalueArray, 0, &curr->bind_indicator_array[0]); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with parameters: hstmt=%p, param_num=%d, param_type=%d, c_type=%d, data_type=%d, param_size=%lu, scale=%d, ivalueArray=%p, bind_indicator_array=%p, and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_LONG, curr->data_type, curr->param_size, curr->scale, curr->ivalueArray, curr->bind_indicator_array, rc); + LogMsg(DEBUG, messageStr, fileName); } else { curr->ivalue = 0; - + snprintf(messageStr, sizeof(messageStr), "Processing single value: ivalue=%d", curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_LONG, curr->data_type, curr->param_size, curr->scale, &curr->ivalue, 0, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with parameters: hstmt=%p, param_num=%d, param_type=%d, c_type=%d, data_type=%d, param_size=%lu, scale=%d, ivalue=%d, and returne rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_LONG, curr->data_type, curr->param_size, curr->scale, curr->ivalue, rc); + LogMsg(DEBUG, messageStr, fileName); } if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { @@ -5780,23 +7166,36 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py } curr->data_type = SQL_C_LONG; + LogMsg(DEBUG, "Updated curr->data_type to SQL_C_LONG", fileName); break; case PYTHON_TRUE: + snprintf(messageStr, sizeof(messageStr), "Handling PYTHON_TRUE case with type=%d", type); + LogMsg(DEBUG, messageStr, fileName); if(TYPE(bind_data) == PYTHON_LIST) { Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "PYTHON_LIST detected with size: %zd", n); + LogMsg(DEBUG, messageStr, fileName); curr->ivalueArray = (SQLINTEGER *)ALLOC_N(SQLINTEGER, n); curr->bind_indicator_array = (SQLINTEGER *) ALLOC_N(SQLINTEGER, n); for (i = 0; i < n; i++) { item = PyList_GetItem(bind_data, i); + snprintf(messageStr, sizeof(messageStr), "List index %d, item pointer: %p", i, (void*)item); + LogMsg(DEBUG, messageStr, fileName); if (TYPE(item) == PYTHON_NIL){ curr->ivalueArray[i] = NULL; curr->bind_indicator_array[i] = SQL_NULL_DATA; + snprintf(messageStr, sizeof(messageStr), "List item index %d is PYTHON_NIL: ivalueArray[%d]=NULL, bind_indicator_array[%d]=SQL_NULL_DATA", + i, i, i); + LogMsg(DEBUG, messageStr, fileName); } else { curr->ivalueArray[i] = PyLong_AsLong(item); curr->bind_indicator_array[i] = SQL_NTS; + snprintf(messageStr, sizeof(messageStr), "Processed list item index %d: ivalueArray[%d]=%d, bind_indicator_array[%d]=SQL_NTS", + i, i, curr->ivalueArray[i], i); + LogMsg(DEBUG, messageStr, fileName); } } @@ -5805,16 +7204,23 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->param_type, SQL_C_LONG, curr->data_type, curr->param_size, curr->scale, curr->ivalueArray, 0, &curr->bind_indicator_array[0]); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with parameters: hstmt=%p, param_num=%d, param_type=%d, c_type=%d, data_type=%d, param_size=%lu, scale=%d, ivalueArray=%p, bind_indicator_array=%p, and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_LONG, curr->data_type, curr->param_size, curr->scale, curr->ivalueArray, curr->bind_indicator_array, rc); + LogMsg(DEBUG, messageStr, fileName); } else { curr->ivalue = 1; - + snprintf(messageStr, sizeof(messageStr), "Single value case: ivalue set to %d", curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_LONG, curr->data_type, curr->param_size, curr->scale, &curr->ivalue, 0, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with parameters: hstmt=%p, param_num=%d, param_type=%d, c_type=%d, data_type=%d, param_size=%lu, scale=%d, ivalue=%d, and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_LONG, curr->data_type, curr->param_size, curr->scale, curr->ivalue, rc); + LogMsg(DEBUG, messageStr, fileName); } if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { @@ -5822,22 +7228,34 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py rc, 1, NULL, -1, 1); } curr->data_type = SQL_C_LONG; + LogMsg(DEBUG, "Updated curr->data_type to SQL_C_LONG", fileName); break; case PYTHON_FLOAT: + snprintf(messageStr, sizeof(messageStr), "Handling PYTHON_FLOAT case with type=%d", type); + LogMsg(DEBUG, messageStr, fileName); if(TYPE(bind_data) == PYTHON_LIST) { Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "PYTHON_LIST detected with size: %zd", n); + LogMsg(DEBUG, messageStr, fileName); curr->fvalueArray = (double *)ALLOC_N(double, n); curr->bind_indicator_array = (SQLINTEGER *) ALLOC_N(SQLINTEGER, n); for (i = 0; i < n; i++) { item = PyList_GetItem(bind_data, i); + snprintf(messageStr, sizeof(messageStr), "List index %d, item pointer: %p", i, (void*)item); + LogMsg(DEBUG, messageStr, fileName); if (TYPE(item) == PYTHON_NIL){ curr->bind_indicator_array[i] = SQL_NULL_DATA; + snprintf(messageStr, sizeof(messageStr), "List item index %d is PYTHON_NIL: bind_indicator_array[%d]=SQL_NULL_DATA", i, i); + LogMsg(DEBUG, messageStr, fileName); } else { curr->fvalueArray[i] = PyFloat_AsDouble(item); curr->bind_indicator_array[i] = SQL_NTS; + snprintf(messageStr, sizeof(messageStr), "Processed list item index %d: fvalueArray[%d]=%f, bind_indicator_array[%d]=SQL_NTS", + i, i, curr->fvalueArray[i], i); + LogMsg(DEBUG, messageStr, fileName); } } @@ -5846,16 +7264,23 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->param_type, SQL_C_DOUBLE, curr->data_type, curr->param_size, curr->scale, curr->fvalueArray, 0, &curr->bind_indicator_array[0]); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with parameters: hstmt=%p, param_num=%d, param_type=%d, c_type=%d, data_type=%d, param_size=%lu, scale=%d, fvalueArray=%p, bind_indicator_array=%p, and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_DOUBLE, curr->data_type, curr->param_size, curr->scale, curr->fvalueArray, curr->bind_indicator_array, rc); + LogMsg(DEBUG, messageStr, fileName); } else { curr->fvalue = PyFloat_AsDouble(bind_data); - + snprintf(messageStr, sizeof(messageStr), "Single float value: fvalue=%f", curr->fvalue); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_DOUBLE, curr->data_type, curr->param_size, curr->scale, &curr->fvalue, 0, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with parameters: hstmt=%p, param_num=%d, param_type=%d, c_type=%d, data_type=%d, param_size=%lu, scale=%d, fvalue=%f, and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_DOUBLE, curr->data_type, curr->param_size, curr->scale, curr->fvalue, rc); + LogMsg(DEBUG, messageStr, fileName); } if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { @@ -5863,15 +7288,20 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py rc, 1, NULL, -1, 1); } curr->data_type = SQL_C_DOUBLE; + LogMsg(DEBUG, "Updated curr->data_type to SQL_C_DOUBLE", fileName); break; case PYTHON_UNICODE: { + snprintf(messageStr, sizeof(messageStr), "Handling PYTHON_UNICODE case with type=%d", type); + LogMsg(DEBUG, messageStr, fileName); /* To Bind array of values */ if(TYPE(bind_data) == PYTHON_LIST) { int isNewBuffer, param_size = 0; Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "PYTHON_LIST detected with size: %zd", n); + LogMsg(DEBUG, messageStr, fileName); curr->uvalue = (SQLWCHAR *)ALLOC_N(SQLWCHAR, curr->param_size * (n)); curr->bind_indicator_array = (SQLINTEGER *) ALLOC_N(SQLINTEGER, n); memset(curr->uvalue , 0, sizeof(SQLWCHAR) * curr->param_size * n); @@ -5879,8 +7309,12 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py for (i = 0; i < n; i++) { item = PyList_GetItem(bind_data, i); + snprintf(messageStr, sizeof(messageStr), "Processing list index %d, item pointer: %p", i, (void*)item); + LogMsg(DEBUG, messageStr, fileName); if (TYPE(item) == PYTHON_NIL){ curr->bind_indicator_array[i] = SQL_NULL_DATA; + snprintf(messageStr, sizeof(messageStr), "Item at index %d is PYTHON_NIL: bind_indicator_array[%d]=SQL_NULL_DATA", i, i); + LogMsg(DEBUG, messageStr, fileName); } else { tmp_uvalue = NULL; dest_uvalue = NULL; @@ -5898,6 +7332,8 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py PyObject_AsReadBuffer(item, (const void **) &tmp_uvalue, &buffer_len); curr->ivalue = buffer_len; #endif + snprintf(messageStr, sizeof(messageStr), "Buffer check: tmp_uvalue=%p, buffer length=%d", (void*)tmp_uvalue, curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -5909,13 +7345,16 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py tmp_uvalue = getUnicodeDataAsSQLWCHAR(item, &isNewBuffer); curr->ivalue = PyUnicode_GetLength(item); curr->ivalue = curr->ivalue * sizeof(SQLWCHAR); + snprintf(messageStr, sizeof(messageStr), "Unicode data: tmp_uvalue=%p, ivalue=%d", (void*)tmp_uvalue, curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); } param_length = curr->ivalue; if (curr->size != 0) { curr->ivalue = (curr->size + 1) * sizeof(SQLWCHAR); } - + snprintf(messageStr, sizeof(messageStr), "Parameter length adjustment: param_length=%d, curr->ivalue=%d", param_length, curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) { if (curr->size == 0) @@ -5938,6 +7377,8 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->ivalue = (curr->param_size + 1) * sizeof(SQLWCHAR); } } + snprintf(messageStr, sizeof(messageStr), "Adjusted ivalue based on SQL_PARAM_OUTPUT/SQL_PARAM_INPUT_OUTPUT: curr->ivalue=%d", curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); } } @@ -5961,15 +7402,21 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py PyMem_Del(tmp_uvalue); param_size = param_length; } - + snprintf(messageStr, sizeof(messageStr), "Memory copy results: dest_uvalue=%p, param_size=%d", (void*)dest_uvalue, param_size); + LogMsg(DEBUG, messageStr, fileName); switch( curr->data_type ) { case SQL_CLOB: case SQL_DBCLOB: + snprintf(messageStr, sizeof(messageStr), "Processing SQL_CLOB or SQL_DBCLOB: param_type=%d, data_type=%d", curr->param_type, curr->data_type); + LogMsg(DEBUG, messageStr, fileName); if(curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) { curr->bind_indicator_array[i] = param_length; paramValuePtr = (SQLPOINTER)curr->uvalue; + snprintf(messageStr, sizeof(messageStr), "SQL_PARAM_OUTPUT or SQL_PARAM_INPUT_OUTPUT: bind_indicator_array[%d]=%d, paramValuePtr=%p", + i, curr->bind_indicator_array[i], (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -5979,15 +7426,24 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py #else paramValuePtr = (SQLPOINTER)&(curr->uvalue); #endif + snprintf(messageStr, sizeof(messageStr), "Non SQL_PARAM_OUTPUT/SQL_PARAM_INPUT_OUTPUT: bind_indicator_array[%d]=%d, paramValuePtr=%p", + i, curr->bind_indicator_array[i], (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } valueType = SQL_C_WCHAR; + LogMsg(DEBUG, "Set valueType to SQL_C_WCHAR", fileName); break; case SQL_BLOB: + snprintf(messageStr, sizeof(messageStr), "Processing SQL_BLOB: param_type=%d, data_type=%d", curr->param_type, curr->data_type); + LogMsg(DEBUG, messageStr, fileName); if (curr->param_type == SQL_PARAM_OUTPUT ||curr->param_type == SQL_PARAM_INPUT_OUTPUT) { curr->bind_indicator_array[i] = param_length; paramValuePtr = (SQLPOINTER)curr->uvalue; + snprintf(messageStr, sizeof(messageStr), "SQL_PARAM_OUTPUT or SQL_PARAM_INPUT_OUTPUT: bind_indicator_array[%d]=%d, paramValuePtr=%p", + i, curr->bind_indicator_array[i], (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -5997,8 +7453,12 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py #else paramValuePtr = (SQLPOINTER)&(curr->uvalue); #endif + snprintf(messageStr, sizeof(messageStr), "Non SQL_PARAM_OUTPUT/SQL_PARAM_INPUT_OUTPUT: bind_indicator_array[%d]=%d, paramValuePtr=%p", + i, curr->bind_indicator_array[i], (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } valueType = SQL_C_BINARY; + LogMsg(DEBUG, "Set valueType to SQL_C_BINARY", fileName); break; case SQL_BINARY: @@ -6006,19 +7466,31 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py case SQL_LONGVARBINARY: #endif /* PASE */ case SQL_VARBINARY: + snprintf(messageStr, sizeof(messageStr), "Processing SQL_BINARY, SQL_LONGVARBINARY or SQL_VARBINARY: param_length=%d", param_length); + LogMsg(DEBUG, messageStr, fileName); /* account for bin_mode settings as well */ curr->bind_indicator_array[i] = param_length; valueType = SQL_C_BINARY; paramValuePtr = (SQLPOINTER)curr->uvalue; + snprintf(messageStr, sizeof(messageStr), "Set bind_indicator_array[%d]=%d, valueType=%d, paramValuePtr=%p", + i, curr->bind_indicator_array[i], valueType, (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_XML: + snprintf(messageStr, sizeof(messageStr), "Processing SQL_XML: param_length=%d", param_length); + LogMsg(DEBUG, messageStr, fileName); curr->bind_indicator_array[i] = param_length; paramValuePtr = (SQLPOINTER)curr->uvalue; valueType = SQL_C_WCHAR; + snprintf(messageStr, sizeof(messageStr), "Set bind_indicator_array[%d]=%d, valueType=%d, paramValuePtr=%p", + i, curr->bind_indicator_array[i], valueType, (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_TYPE_TIMESTAMP: + snprintf(messageStr, sizeof(messageStr), "Processing SQL_TYPE_TIMESTAMP: param_length=%d", param_length); + LogMsg(DEBUG, messageStr, fileName); valueType = SQL_C_WCHAR; if( param_length == 0) { @@ -6033,12 +7505,20 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py dest_uvalue[20] = ' '; } paramValuePtr = (SQLPOINTER)(curr->uvalue); + snprintf(messageStr, sizeof(messageStr), "Set bind_indicator_array[%d]=%d, valueType=%d, paramValuePtr=%p", + i, curr->bind_indicator_array[i], valueType, (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); break; default: + snprintf(messageStr, sizeof(messageStr), "Default case for data_type: %d", curr->data_type); + LogMsg(DEBUG, messageStr, fileName); valueType = SQL_C_WCHAR; curr->bind_indicator_array[i] = param_length; paramValuePtr = (SQLPOINTER)(curr->uvalue); + snprintf(messageStr, sizeof(messageStr), + "Set bind_indicator_array[%d]=%d, valueType=%d, paramValuePtr=%p", i, curr->bind_indicator_array[i], valueType, (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } } } @@ -6048,25 +7528,36 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->data_type, curr->param_size, curr->scale, paramValuePtr, param_size, &curr->bind_indicator_array[0]); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with parameters: hstmt=%p, param_num=%d, param_type=%d, valueType=%d, data_type=%d, param_size=%d, scale=%d, paramValuePtr=%p, param_size=%d, bind_indicator_array=%p, and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, valueType, curr->data_type, curr->param_size, curr->scale, paramValuePtr, param_size, curr->bind_indicator_array, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Updated curr->data_type to %d", curr->data_type); + LogMsg(DEBUG, messageStr, fileName); curr->data_type = valueType; } else /* To bind scalar values */ { int isNewBuffer; + snprintf(messageStr, sizeof(messageStr), "Binding scalar values: data_type=%d, param_type=%d", curr->data_type, curr->param_type); + LogMsg(DEBUG, messageStr, fileName); if(PyObject_CheckBuffer(bind_data) && (curr->data_type == SQL_BLOB || curr->data_type == SQL_BINARY || curr->data_type == SQL_VARBINARY)) { #if PY_MAJOR_VERSION >= 3 Py_buffer tmp_buffer; PyObject_GetBuffer(bind_data, &tmp_buffer, PyBUF_SIMPLE); curr->uvalue = tmp_buffer.buf; curr->ivalue = tmp_buffer.len; + snprintf(messageStr, sizeof(messageStr), "buffer: uvalue=%p, ivalue=%d", (void*)curr->uvalue, curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); #else PyObject_AsReadBuffer(bind_data, (const void **) &(curr->uvalue), &buffer_len); curr->ivalue = buffer_len; + snprintf(messageStr, sizeof(messageStr), "Python 2 buffer: uvalue=%p, ivalue=%d", (void*)curr->uvalue, curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); #endif } else { if(curr->uvalue != NULL) { @@ -6076,10 +7567,16 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->uvalue = getUnicodeDataAsSQLWCHAR(bind_data, &isNewBuffer); curr->ivalue = PyUnicode_GetLength(bind_data); curr->ivalue = curr->ivalue * sizeof(SQLWCHAR); + snprintf(messageStr, sizeof(messageStr), "New uvalue=%p, ivalue=%d", (void*)curr->uvalue, curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); } param_length = curr->ivalue; + snprintf(messageStr, sizeof(messageStr), "Calculated param_length=%d", param_length); + LogMsg(DEBUG, messageStr, fileName); if (curr->size != 0) { curr->ivalue = (curr->size + 1) * sizeof(SQLWCHAR); + snprintf(messageStr, sizeof(messageStr), "Adjusted ivalue for size: %d", curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); } if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) { @@ -6091,10 +7588,14 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py || (curr->data_type == SQL_VARBINARY) || (curr->data_type == SQL_XML)) { if (curr->ivalue <= curr->param_size) { curr->ivalue = curr->param_size + sizeof(SQLWCHAR); + snprintf(messageStr, sizeof(messageStr), "Increased ivalue due to size adjustment: %d", curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); } } else { if (curr->ivalue <= (curr->param_size * sizeof(SQLWCHAR))) { curr->ivalue = (curr->param_size + 1) * sizeof(SQLWCHAR); + snprintf(messageStr, sizeof(messageStr), "Increased ivalue for other data types: %d", curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); } } } @@ -6105,19 +7606,27 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py SQLWCHAR* tmp = (SQLWCHAR*)ALLOC_N(SQLWCHAR, curr->ivalue + 1); memcpy(tmp, curr->uvalue, (param_length + sizeof(SQLWCHAR))); curr->uvalue = tmp; + snprintf(messageStr, sizeof(messageStr), "Copied uvalue to new buffer, tmp=%p", (void*)tmp); + LogMsg(DEBUG, messageStr, fileName); } else if (param_length <= curr->param_size) { SQLWCHAR* tmp = (SQLWCHAR*)ALLOC_N(SQLWCHAR, curr->ivalue + 1); memcpy(tmp, curr->uvalue, (param_length + sizeof(SQLWCHAR))); PyMem_Del(curr->uvalue); curr->uvalue = tmp; + snprintf(messageStr, sizeof(messageStr), "Copied uvalue to new buffer with size adjustment, tmp=%p", (void*)tmp); + LogMsg(DEBUG, messageStr, fileName); } switch( curr->data_type){ case SQL_CLOB: case SQL_DBCLOB: + snprintf(messageStr, sizeof(messageStr), "Processing SQL_CLOB or SQL_DBCLOB: param_type=%d", curr->param_type); + LogMsg(DEBUG, messageStr, fileName); if(curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT){ curr->bind_indicator = param_length; paramValuePtr = (SQLPOINTER)curr->uvalue; + snprintf(messageStr, sizeof(messageStr), "SQL_PARAM_OUTPUT/SQL_PARAM_INPUT_OUTPUT: bind_indicator=%d, paramValuePtr=%p", curr->bind_indicator, (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } else { curr->bind_indicator = SQL_DATA_AT_EXEC; #ifndef PASE @@ -6125,14 +7634,23 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py #else paramValuePtr = (SQLPOINTER)&(curr); #endif + snprintf(messageStr, sizeof(messageStr), "Non SQL_PARAM_OUTPUT/SQL_PARAM_INPUT_OUTPUT: bind_indicator=%d, paramValuePtr=%p", + curr->bind_indicator, (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } valueType = SQL_C_WCHAR; + LogMsg(DEBUG, "Set valueType to SQL_C_WCHAR", fileName); break; case SQL_BLOB: + snprintf(messageStr, sizeof(messageStr), "Handling SQL_BLOB: param_type=%d, param_length=%d", curr->param_type, param_length); + LogMsg(DEBUG, messageStr, fileName); if (curr->param_type == SQL_PARAM_OUTPUT ||curr->param_type == SQL_PARAM_INPUT_OUTPUT) { curr->bind_indicator = param_length; paramValuePtr = (SQLPOINTER)curr; + snprintf(messageStr, sizeof(messageStr), "SQL_PARAM_OUTPUT/SQL_PARAM_INPUT_OUTPUT: bind_indicator=%d, paramValuePtr=%p", + curr->bind_indicator, (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } else { curr->bind_indicator = SQL_DATA_AT_EXEC; #ifndef PASE @@ -6140,8 +7658,11 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py #else paramValuePtr = (SQLPOINTER)&(curr); #endif + snprintf(messageStr, sizeof(messageStr), "Non SQL_PARAM_OUTPUT/SQL_PARAM_INPUT_OUTPUT: bind_indicator=%d, paramValuePtr=%p", curr->bind_indicator, (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } valueType = SQL_C_BINARY; + LogMsg(DEBUG, "Set valueType to SQL_C_BINARY", fileName); break; case SQL_BINARY: @@ -6149,56 +7670,85 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py case SQL_LONGVARBINARY: #endif /* PASE */ case SQL_VARBINARY: + snprintf(messageStr, sizeof(messageStr), "Handling SQL_BINARY/SQL_LONGVARBINARY/SQL_VARBINARY: param_length=%d", param_length); + LogMsg(DEBUG, messageStr, fileName); /* account for bin_mode settings as well */ curr->bind_indicator = param_length; valueType = SQL_C_BINARY; paramValuePtr = (SQLPOINTER)curr->uvalue; + snprintf(messageStr, sizeof(messageStr), "SQL_BINARY/SQL_LONGVARBINARY/SQL_VARBINARY: bind_indicator=%d, paramValuePtr=%p", + curr->bind_indicator, (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_XML: + snprintf(messageStr, sizeof(messageStr), "Handling SQL_XML: param_length=%d", param_length); + LogMsg(DEBUG, messageStr, fileName); curr->bind_indicator = param_length; paramValuePtr = (SQLPOINTER)curr->uvalue; valueType = SQL_C_WCHAR; + snprintf(messageStr, sizeof(messageStr), "SQL_XML: bind_indicator=%d, paramValuePtr=%p, valueType=%d", curr->bind_indicator, (void*)paramValuePtr, valueType); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_TYPE_TIMESTAMP: + snprintf(messageStr, sizeof(messageStr), "Handling SQL_TYPE_TIMESTAMP: param_length=%d, uvalue[10]=%c", param_length, curr->uvalue[10]); + LogMsg(DEBUG, messageStr, fileName); valueType = SQL_C_WCHAR; if( param_length == 0) { curr->bind_indicator = SQL_NULL_DATA; + snprintf(messageStr, sizeof(messageStr), "SQL_TYPE_TIMESTAMP with zero param_length: bind_indicator=%d", curr->bind_indicator); + LogMsg(DEBUG, messageStr, fileName); } else { curr->bind_indicator = param_length; + snprintf(messageStr, sizeof(messageStr), "SQL_TYPE_TIMESTAMP: bind_indicator=%d", curr->bind_indicator); + LogMsg(DEBUG, messageStr, fileName); } if(curr->uvalue[10] == 'T'){ curr->uvalue[10] = ' '; } paramValuePtr = (SQLPOINTER)(curr->uvalue); + snprintf(messageStr, sizeof(messageStr), "SQL_TYPE_TIMESTAMP: paramValuePtr=%p", (void*)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); break; default: + snprintf(messageStr, sizeof(messageStr), "Handling default case: param_length=%d", param_length); + LogMsg(DEBUG, messageStr, fileName); valueType = SQL_C_WCHAR; curr->bind_indicator = param_length; paramValuePtr = (SQLPOINTER)(curr->uvalue); + snprintf(messageStr, sizeof(messageStr), "Default case: bind_indicator=%d, paramValuePtr=%p, valueType=%d", curr->bind_indicator, (void*)paramValuePtr, valueType); + LogMsg(DEBUG, messageStr, fileName); } Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, valueType, curr->data_type, curr->param_size, curr->scale, paramValuePtr, curr->ivalue, &(curr->bind_indicator)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter: param_num=%d, param_type=%d, valueType=%d, data_type=%d, param_size=%d, scale=%d, paramValuePtr=%p, ivalue=%d, bind_indicator=%d and returned rc=%d", + curr->param_num, curr->param_type, valueType, curr->data_type, curr->param_size, curr->scale, paramValuePtr, curr->ivalue, curr->bind_indicator, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } curr->data_type = valueType; + snprintf(messageStr, sizeof(messageStr), "Updated curr->data_type to %d", curr->data_type); + LogMsg(DEBUG, messageStr, fileName); } } break; case PYTHON_STRING: { + snprintf(messageStr, sizeof(messageStr), "Handling PYTHON_STRING: TYPE(bind_data)=%d, curr->param_size=%d", TYPE(bind_data), curr->param_size); + LogMsg(DEBUG, messageStr, fileName); /* To Bind array of values */ if(TYPE(bind_data) == PYTHON_LIST) { Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "Binding array of values: n=%zd", n); + LogMsg(DEBUG, messageStr, fileName); curr->svalue = (char *)ALLOC_N(char, curr->param_size * (n)); curr->bind_indicator_array = (SQLINTEGER *) ALLOC_N(SQLINTEGER, n); memset(curr->svalue , 0, curr->param_size * n); @@ -6206,7 +7756,8 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py for (i = 0; i < n; i++) { item = PyList_GetItem(bind_data, i); - + snprintf(messageStr, sizeof(messageStr), "Processing list item %d: TYPE(item)=%d", i, TYPE(item)); + LogMsg(DEBUG, messageStr, fileName); if (TYPE(item) == PYTHON_NIL){ curr->bind_indicator_array[i] = SQL_NULL_DATA; } else { @@ -6238,6 +7789,8 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->ivalue = strlen(tmp_svalue); } param_length = curr->ivalue; + snprintf(messageStr, sizeof(messageStr), "Item %d: tmp_svalue=%p, tmp_svalue_len=%d, param_length=%d", i, (void *)tmp_svalue, curr->ivalue, param_length); + LogMsg(DEBUG, messageStr, fileName); /* * * An extra parameter is given by the client to pick the size of the * * string returned. The string is then truncate past that size. @@ -6261,15 +7814,20 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py dest_svalue = &curr->svalue[0] + (curr->param_size * i); dest_svalue = memcpy(dest_svalue, tmp_svalue, param_length); - + snprintf(messageStr, sizeof(messageStr), "Item %d: dest_svalue=%p, valueType=%d", i, (void *)dest_svalue, valueType); + LogMsg(DEBUG, messageStr, fileName); switch ( curr->data_type ) { case SQL_CLOB: case SQL_DBCLOB: + snprintf(messageStr, sizeof(messageStr), "Processing SQL_CLOB/SQL_DBCLOB case: curr->param_type=%d, curr->data_type=%d, curr->ivalue=%d, param_length=%d", curr->param_type, curr->data_type, curr->ivalue, param_length); + LogMsg(DEBUG, messageStr, fileName); if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) { curr->bind_indicator_array[i] = param_length; paramValuePtr = (SQLPOINTER)curr->svalue; + snprintf(messageStr, sizeof(messageStr), "For OUTPUT/INPUT_OUTPUT: curr->bind_indicator_array[%d]=%d, paramValuePtr=%p", i, curr->bind_indicator_array[i], (void *)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -6282,16 +7840,25 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py #else paramValuePtr = (SQLPOINTER)&(curr->svalue); #endif + snprintf(messageStr, sizeof(messageStr), "For other param_type: curr->bind_indicator_array[%d]=%d, paramValuePtr=%p", i, curr->bind_indicator_array[i], (void *)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } valueType = SQL_C_CHAR; + snprintf(messageStr, sizeof(messageStr), "updated valueType to %d", valueType); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_BLOB: + snprintf(messageStr, sizeof(messageStr), "Processing SQL_BLOB case: curr->param_type=%d, curr->data_type=%d, curr->ivalue=%d, param_length=%d", curr->param_type, curr->data_type, curr->ivalue, param_length); + LogMsg(DEBUG, messageStr, fileName); if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) { curr->ivalue = curr->ivalue - 1; curr->bind_indicator_array[i] = param_length; paramValuePtr = (SQLPOINTER)curr->svalue; + snprintf(messageStr, sizeof(messageStr), "For OUTPUT/INPUT_OUTPUT: curr->ivalue=%d, curr->bind_indicator_array[%d]=%d, paramValuePtr=%p", + curr->ivalue, i, curr->bind_indicator_array[i], (void *)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -6301,8 +7868,12 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py #else paramValuePtr = (SQLPOINTER)&(curr->svalue); #endif + snprintf(messageStr, sizeof(messageStr), "For other param_type: curr->bind_indicator_array[%d]=%d, paramValuePtr=%p", i, curr->bind_indicator_array[i], (void *)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } valueType = SQL_C_BINARY; + snprintf(messageStr, sizeof(messageStr), "Updated valueType to %d", valueType); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_BINARY: @@ -6311,22 +7882,33 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py #endif /* PASE */ case SQL_VARBINARY: case SQL_XML: + snprintf(messageStr, sizeof(messageStr), "Processing SQL_BINARY/SQL_LONGVARBINARY/SQL_VARBINARY/SQL_XML case: curr->param_type=%d, curr->data_type=%d, curr->ivalue=%d, param_length=%d", + curr->param_type, curr->data_type, curr->ivalue, param_length); + LogMsg(DEBUG, messageStr, fileName); /* account for bin_mode settings as well */ curr->bind_indicator_array[i] = curr->ivalue; if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) { curr->ivalue = curr->ivalue - 1; curr->bind_indicator_array[i] = param_length; + snprintf(messageStr, sizeof(messageStr), "For OUTPUT/INPUT_OUTPUT: curr->ivalue=%d, curr->bind_indicator_array[%d]=%d", curr->ivalue, i, curr->bind_indicator_array[i]); + LogMsg(DEBUG, messageStr, fileName); } valueType = SQL_C_BINARY; paramValuePtr = (SQLPOINTER)curr->svalue; + snprintf(messageStr, sizeof(messageStr), "Updated SQL_BINARY/SQL_LONGVARBINARY/SQL_VARBINARY/SQL_XML case: valueType=%d, paramValuePtr=%p", + valueType, (void *)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); break; /* This option should handle most other types such as DATE, * * VARCHAR etc * */ case SQL_TYPE_TIMESTAMP: + snprintf(messageStr, sizeof(messageStr), "Processing SQL_TYPE_TIMESTAMP case: curr->param_type=%d, curr->data_type=%d, curr->ivalue=%d, param_length=%d", + curr->param_type, curr->data_type, curr->ivalue, param_length); + LogMsg(DEBUG, messageStr, fileName); valueType = SQL_C_CHAR; curr->bind_indicator_array[i] = curr->ivalue; if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) @@ -6339,15 +7921,23 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py { curr->bind_indicator_array[i] = SQL_NTS; } + snprintf(messageStr, sizeof(messageStr), "For OUTPUT/INPUT_OUTPUT: curr->bind_indicator_array[%d]=%d", i, curr->bind_indicator_array[i]); + LogMsg(DEBUG, messageStr, fileName); } if(dest_svalue[10] == 'T') { dest_svalue[10] = ' '; } paramValuePtr = (SQLPOINTER)(curr->svalue); + snprintf(messageStr, sizeof(messageStr), "updated SQL_TYPE_TIMESTAMP case: valueType to %d, paramValuePtr to %p, dest_svalue[10]=%c", + valueType, (void *)paramValuePtr, dest_svalue[10]); + LogMsg(DEBUG, messageStr, fileName); break; default: + snprintf(messageStr, sizeof(messageStr),"Processing default case: curr->data_type=%d, curr->param_type=%d, curr->ivalue=%d", + curr->data_type, curr->param_type, curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); valueType = SQL_C_CHAR; curr->bind_indicator_array[i] = curr->ivalue; if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) @@ -6355,6 +7945,8 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->bind_indicator_array[i] = SQL_NTS; } paramValuePtr = (SQLPOINTER)(curr->svalue); + snprintf(messageStr, sizeof(messageStr), "Exiting default case: valueType=%d, paramValuePtr=%p", valueType, (void *)paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } } } @@ -6364,16 +7956,23 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->param_type, valueType, curr->data_type, curr->param_size, curr->scale, paramValuePtr, curr->param_size, &curr->bind_indicator_array[0]); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLBindParameter called with parameters: stmt_handle=%p, param_num=%d, param_type=%d, valueType=%d, data_type=%d, param_size=%d, scale=%d, paramValuePtr=%p, param_size=%d, bind_indicator_array[0]=%d, and returned rc=%d", + (void *)stmt_res->hstmt, curr->param_num, curr->param_type, valueType, curr->data_type, + curr->param_size, curr->scale, (void *)paramValuePtr, curr->param_size, curr->bind_indicator_array[0], rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } curr->data_type = valueType; + snprintf(messageStr, sizeof(messageStr), "Updated curr->data_type: valueType=%d", valueType); + LogMsg(DEBUG, messageStr, fileName); } else /* To bind scalar values */ { char* tmp; + snprintf(messageStr, sizeof(messageStr), "Binding scalar values: bind_data=%p, curr->data_type=%d", bind_data, curr->data_type); + LogMsg(DEBUG, messageStr, fileName); if (PyObject_CheckBuffer(bind_data) && (curr->data_type == SQL_BLOB || curr->data_type == SQL_BINARY || curr->data_type == SQL_VARBINARY) ) @@ -6399,6 +7998,8 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->ivalue = strlen(curr->svalue); } param_length = curr->ivalue; + snprintf(messageStr, sizeof(messageStr), "param_length=%d, curr->size=%d", param_length, curr->size); + LogMsg(DEBUG, messageStr, fileName); /* * An extra parameter is given by the client to pick the size of the * string returned. The string is then truncate past that size. @@ -6424,16 +8025,21 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py memset(tmp, 0, curr->ivalue+1); curr->svalue = memcpy(tmp, curr->svalue, param_length); curr->svalue[param_length] = '\0'; - + snprintf(messageStr, sizeof(messageStr), "After allocation: curr->svalue=%p, curr->ivalue=%d", curr->svalue, curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); switch ( curr->data_type ) { case SQL_CLOB: case SQL_DBCLOB: + snprintf(messageStr, sizeof(messageStr), "Data type: SQL_CLOB or SQL_DBCLOB. param_type=%d, param_length=%d, curr->svalue=%p", curr->param_type, param_length, curr->svalue); + LogMsg(DEBUG, messageStr, fileName); if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) { curr->bind_indicator = param_length; paramValuePtr = (SQLPOINTER)curr->svalue; + snprintf(messageStr, sizeof(messageStr), "Binding for SQL_CLOB or SQL_DBCLOB. bind_indicator=%d, paramValuePtr=%p", curr->bind_indicator, paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -6446,17 +8052,24 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py #else paramValuePtr = (SQLPOINTER)&(curr); #endif + snprintf(messageStr, sizeof(messageStr), "Binding for SQL_CLOB or SQL_DBCLOB at exec. bind_indicator=%d, paramValuePtr=%p", curr->bind_indicator, paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } valueType = SQL_C_CHAR; + LogMsg(DEBUG, "updated valueType to SQL_C_CHAR", fileName); break; case SQL_BLOB: + snprintf(messageStr, sizeof(messageStr), "Data type: SQL_BLOB. param_type=%d, curr->ivalue=%d", curr->param_type, curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) { curr->ivalue = curr->ivalue -1; curr->bind_indicator = param_length; paramValuePtr = (SQLPOINTER)curr->svalue; + snprintf(messageStr, sizeof(messageStr), "Binding for SQL_BLOB. ivalue=%d, bind_indicator=%d, paramValuePtr=%p", curr->ivalue, curr->bind_indicator, paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -6466,8 +8079,11 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py #else paramValuePtr = (SQLPOINTER)&(curr); #endif + snprintf(messageStr, sizeof(messageStr), "Binding for SQL_BLOB at exec. bind_indicator=%d, paramValuePtr=%p", curr->bind_indicator, paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } valueType = SQL_C_BINARY; + LogMsg(DEBUG, "updated valueType to SQL_C_BINARY", fileName); break; case SQL_BINARY: @@ -6476,22 +8092,30 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py #endif /* PASE */ case SQL_VARBINARY: case SQL_XML: + snprintf(messageStr, sizeof(messageStr), "Data type: SQL_BINARY, SQL_LONGVARBINARY, SQL_VARBINARY, or SQL_XML. param_type=%d, ivalue=%d", curr->param_type, curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); /* account for bin_mode settings as well */ curr->bind_indicator = curr->ivalue; if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) { curr->ivalue = curr->ivalue - 1; curr->bind_indicator = param_length; + snprintf(messageStr, sizeof(messageStr), "Binding for SQL_BINARY or similar. ivalue=%d, bind_indicator=%d", curr->ivalue, curr->bind_indicator); + LogMsg(DEBUG, messageStr, fileName); } valueType = SQL_C_BINARY; paramValuePtr = (SQLPOINTER)curr->svalue; + snprintf(messageStr, sizeof(messageStr), "Value type set to SQL_C_BINARY. valueType=%d, paramValuePtr=%p", valueType, paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); break; /* This option should handle most other types such as DATE, * VARCHAR etc */ case SQL_TYPE_TIMESTAMP: + snprintf(messageStr, sizeof(messageStr), "Data type: SQL_TYPE_TIMESTAMP. param_type=%d, param_length=%d, svalue[10]=%c", curr->param_type, param_length, curr->svalue[10]); + LogMsg(DEBUG, messageStr, fileName); valueType = SQL_C_CHAR; curr->bind_indicator = curr->ivalue; if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) @@ -6504,21 +8128,31 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py { curr->bind_indicator = SQL_NTS; } + snprintf(messageStr, sizeof(messageStr), "Binding for SQL_TYPE_TIMESTAMP. bind_indicator=%d", curr->bind_indicator); + LogMsg(DEBUG, messageStr, fileName); } if(curr->svalue[10] == 'T') { curr->svalue[10] = ' '; } paramValuePtr = (SQLPOINTER)(curr->svalue); + snprintf(messageStr, sizeof(messageStr), "Value type set to SQL_C_CHAR. valueType=%d, paramValuePtr=%p", valueType, paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); break; default: valueType = SQL_C_CHAR; + snprintf(messageStr, sizeof(messageStr), "Default case: data_type=%d", curr->data_type); + LogMsg(DEBUG, messageStr, fileName); curr->bind_indicator = curr->ivalue; if (curr->param_type == SQL_PARAM_OUTPUT || curr->param_type == SQL_PARAM_INPUT_OUTPUT) { curr->bind_indicator = SQL_NTS; + snprintf(messageStr, sizeof(messageStr), "Default binding. bind_indicator=%d", curr->bind_indicator); + LogMsg(DEBUG, messageStr, fileName); } paramValuePtr = (SQLPOINTER)(curr->svalue); + snprintf(messageStr, sizeof(messageStr), "Value type set to SQL_C_CHAR. valueType=%d, paramValuePtr=%p", valueType, paramValuePtr); + LogMsg(DEBUG, messageStr, fileName); } Py_BEGIN_ALLOW_THREADS; @@ -6526,17 +8160,23 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->param_type, valueType, curr->data_type, curr->param_size, curr->scale, paramValuePtr, curr->ivalue, &(curr->bind_indicator)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter with parameters: hstmt=%p, param_num=%d, param_type=%d, valueType=%d, data_type=%d, param_size=%d, scale=%d, paramValuePtr=%p, ivalue=%d, bind_indicator=%p and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, valueType, curr->data_type, curr->param_size, curr->scale, paramValuePtr, curr->ivalue, &(curr->bind_indicator), rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } curr->data_type = valueType; + snprintf(messageStr, sizeof(messageStr), "Updated curr->data_type to valueType. New data_type=%d", curr->data_type); + LogMsg(DEBUG, messageStr, fileName); } } break; case PYTHON_DECIMAL: + snprintf(messageStr, sizeof(messageStr), "Handling PYTHON_DECIMAL case with current data_type=%d", curr->data_type); + LogMsg(DEBUG, messageStr, fileName); if (curr->data_type == SQL_DECIMAL || curr->data_type == SQL_DECFLOAT || curr->data_type == SQL_BIGINT || curr->data_type == SQL_FLOAT || curr->data_type == SQL_DOUBLE){ if(TYPE(bind_data) == PYTHON_LIST) @@ -6550,6 +8190,8 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py else // SQL_DECFLOAT max_precn = curr->param_size; + snprintf(messageStr, sizeof(messageStr), "PYTHON_LIST detected with size: %zd, max_precision=%d", n, max_precn); + LogMsg(DEBUG, messageStr, fileName); if(curr->svalue != NULL) { PyMem_Del(curr->svalue); @@ -6567,8 +8209,12 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py PyObject *tempobj2 = NULL; #endif item = PyList_GetItem(bind_data, i); + snprintf(messageStr, sizeof(messageStr), "Processing list item index %d, item pointer: %p", i, (void*)item); + LogMsg(DEBUG, messageStr, fileName); if (TYPE(item) == PYTHON_NIL){ curr->bind_indicator_array[i] = SQL_NULL_DATA; + snprintf(messageStr, sizeof(messageStr), "List item index %d is PYTHON_NIL: bind_indicator_array[%d]=SQL_NULL_DATA", i, i); + LogMsg(DEBUG, messageStr, fileName); } else { tempobj = PyObject_Str(item); #if PY_MAJOR_VERSION >= 3 @@ -6582,6 +8228,8 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py valueType = SQL_C_CHAR; paramValuePtr = (SQLPOINTER)(curr->svalue); curr->bind_indicator_array[i] = curr->ivalue; + snprintf(messageStr, sizeof(messageStr), "Processed list item index %d: svalue=%s, ivalue=%d, bind_indicator_array[%d]=%d", i, svalue, curr->ivalue, i, curr->bind_indicator_array[i]); + LogMsg(DEBUG, messageStr, fileName); Py_XDECREF(tempobj); } } @@ -6591,7 +8239,9 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->data_type, curr->param_size, curr->scale, paramValuePtr, max_precn, curr->bind_indicator_array); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter for PYTHON_LIST with parameters: hstmt=%p, param_num=%d, param_type=%d, valueType=%d, data_type=%d, param_size=%d, scale=%d, paramValuePtr=%p, max_precn=%d, bind_indicator_array=%p and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, valueType, curr->data_type, curr->param_size, curr->scale, paramValuePtr, max_precn, curr->bind_indicator_array, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT,rc, 1, NULL, -1, 1); @@ -6621,13 +8271,16 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py valueType = SQL_C_CHAR; paramValuePtr = (SQLPOINTER)(curr->svalue); curr->bind_indicator = curr->ivalue; - + snprintf(messageStr, sizeof(messageStr), "Binding scalar value: svalue=%s, ivalue=%d, bind_indicator=%d", curr->svalue, curr->ivalue, curr->bind_indicator); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, valueType, curr->data_type, curr->param_size, curr->scale, paramValuePtr, curr->ivalue, &(curr->bind_indicator)); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter for scalar value with parameters: hstmt=%p, param_num=%d, param_type=%d, valueType=%d, data_type=%d, param_size=%d, scale=%d, paramValuePtr=%p, ivalue=%d, bind_indicator=%p, and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, valueType, curr->data_type, curr->param_size, curr->scale, paramValuePtr, curr->ivalue, &(curr->bind_indicator), rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT,rc, 1, NULL, -1, 1); } @@ -6638,21 +8291,32 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py break; case PYTHON_DATE: + snprintf(messageStr, sizeof(messageStr), "Handling PYTHON_DATE case. Current data_type=%d", curr->data_type); + LogMsg(DEBUG, messageStr, fileName); if(TYPE(bind_data) == PYTHON_LIST) { Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "PYTHON_LIST detected with size: %zd", n); + LogMsg(DEBUG, messageStr, fileName); curr->date_value = ALLOC_N(DATE_STRUCT, n); curr->bind_indicator_array = (SQLINTEGER *) ALLOC_N(SQLINTEGER, n); for (i = 0; i < n; i++) { item = PyList_GetItem(bind_data, i); + snprintf(messageStr, sizeof(messageStr), "Processing list item index %d, item pointer: %p", i, (void*)item); + LogMsg(DEBUG, messageStr, fileName); if (TYPE(item) == PYTHON_NIL){ curr->bind_indicator_array[i] = SQL_NULL_DATA; + snprintf(messageStr, sizeof(messageStr), "List item index %d is PYTHON_NIL: bind_indicator_array[%d]=SQL_NULL_DATA", i, i); + LogMsg(DEBUG, messageStr, fileName); } else { (curr->date_value + i)->year = PyDateTime_GET_YEAR(item); (curr->date_value + i)->month = PyDateTime_GET_MONTH(item); (curr->date_value + i)->day = PyDateTime_GET_DAY(item); curr->bind_indicator_array[i] = SQL_NTS; + snprintf(messageStr, sizeof(messageStr), "List item index %d: year=%d, month=%d, day=%d, bind_indicator_array[%d]=SQL_NTS", + i, (curr->date_value + i)->year, (curr->date_value + i)->month, (curr->date_value + i)->day, i); + LogMsg(DEBUG, messageStr, fileName); } } @@ -6661,6 +8325,9 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->param_type, SQL_C_TYPE_DATE, curr->data_type, curr->param_size, curr->scale, curr->date_value, curr->ivalue, &curr->bind_indicator_array[0]); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter for PYTHON_LIST with parameters: hstmt=%p, param_num=%d, param_type=%d, data_type=%d, param_size=%d, scale=%d, date_value=%p, ivalue=%d, bind_indicator_array=%p and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, curr->data_type, curr->param_size, curr->scale, curr->date_value, curr->ivalue, curr->bind_indicator_array, rc); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -6668,31 +8335,46 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->date_value->year = PyDateTime_GET_YEAR(bind_data); curr->date_value->month = PyDateTime_GET_MONTH(bind_data); curr->date_value->day = PyDateTime_GET_DAY(bind_data); - + snprintf(messageStr, sizeof(messageStr), "Binding scalar value: year=%d, month=%d, day=%d", + curr->date_value->year, curr->date_value->month, curr->date_value->day); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_TYPE_DATE, curr->data_type, curr->param_size, curr->scale, curr->date_value, curr->ivalue, &(curr->bind_indicator)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter for scalar value with parameters: hstmt=%p, param_num=%d, param_type=%d, data_type=%d, param_size=%d, scale=%d, date_value=%p, ivalue=%d, bind_indicator=%p and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, curr->data_type, curr->param_size, curr->scale, curr->date_value, curr->ivalue, &(curr->bind_indicator), rc); + LogMsg(DEBUG, messageStr, fileName); } break; case PYTHON_TIME: + snprintf(messageStr, sizeof(messageStr), "Handling PYTHON_TIME case. Current data_type=%d", curr->data_type); + LogMsg(DEBUG, messageStr, fileName); if(TYPE(bind_data) == PYTHON_LIST) { Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "PYTHON_LIST detected with size: %zd", n); + LogMsg(DEBUG, messageStr, fileName); curr->time_value = ALLOC_N(TIME_STRUCT, n); curr->bind_indicator_array = (SQLINTEGER *) ALLOC_N(SQLINTEGER, n); for (i = 0; i < n; i++) { item = PyList_GetItem(bind_data, i); + snprintf(messageStr, sizeof(messageStr), "Processing list item index %d, item pointer: %p", i, (void*)item); + LogMsg(DEBUG, messageStr, fileName); if (TYPE(item) == PYTHON_NIL){ curr->bind_indicator_array[i] = SQL_NULL_DATA; + snprintf(messageStr, sizeof(messageStr), "List item index %d is PYTHON_NIL: bind_indicator_array[%d]=SQL_NULL_DATA", i, i); + LogMsg(DEBUG, messageStr, fileName); } else { (curr->time_value + i)->hour = PyDateTime_TIME_GET_HOUR(item); (curr->time_value + i)->minute = PyDateTime_TIME_GET_MINUTE(item); (curr->time_value + i)->second = PyDateTime_TIME_GET_SECOND(item); curr->bind_indicator_array[i] = SQL_NTS; + snprintf(messageStr, sizeof(messageStr), "List item index %d: hour=%d, minute=%d, second=%d, bind_indicator_array[%d]=SQL_NTS", i, (curr->time_value + i)->hour, (curr->time_value + i)->minute, (curr->time_value + i)->second, i); + LogMsg(DEBUG, messageStr, fileName); } } @@ -6701,6 +8383,9 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->param_type, SQL_C_TYPE_TIME, curr->data_type, curr->param_size, curr->scale, curr->time_value, curr->ivalue, &curr->bind_indicator_array[0]); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter for PYTHON_LIST with parameters: hstmt=%p, param_num=%d, param_type=%d, data_type=%d, param_size=%d, scale=%d, time_value=%p, ivalue=%d, bind_indicator_array=%p and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, curr->data_type, curr->param_size, curr->scale, curr->time_value, curr->ivalue, curr->bind_indicator_array, rc); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -6708,27 +8393,40 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->time_value->hour = PyDateTime_TIME_GET_HOUR(bind_data); curr->time_value->minute = PyDateTime_TIME_GET_MINUTE(bind_data); curr->time_value->second = PyDateTime_TIME_GET_SECOND(bind_data); - + snprintf(messageStr, sizeof(messageStr), "Binding scalar value: hour=%d, minute=%d, second=%d", + curr->time_value->hour, curr->time_value->minute, curr->time_value->second); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_TYPE_TIME, curr->data_type, curr->param_size, curr->scale, curr->time_value, curr->ivalue, &(curr->bind_indicator)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter for scalar value with parameters: hstmt=%p, param_num=%d, param_type=%d, data_type=%d, param_size=%d, scale=%d, time_value=%p, ivalue=%d, bind_indicator=%p and returned rc=%d", + stmt_res->hstmt, curr->param_num, curr->param_type, curr->data_type, curr->param_size, curr->scale, curr->time_value, curr->ivalue, &(curr->bind_indicator), rc); + LogMsg(DEBUG, messageStr, fileName); } break; case PYTHON_TIMESTAMP: + snprintf(messageStr, sizeof(messageStr), "Handling PYTHON_TIMESTAMP case. Current data_type=%d", curr->data_type); + LogMsg(DEBUG, messageStr, fileName); if(TYPE(bind_data) == PYTHON_LIST) { Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "PYTHON_LIST detected with size: %zd", n); + LogMsg(DEBUG, messageStr, fileName); curr->ts_value = ALLOC_N(TIMESTAMP_STRUCT, n); curr->bind_indicator_array = (SQLINTEGER *) ALLOC_N(SQLINTEGER, n); for (i = 0; i < n; i++) { item = PyList_GetItem(bind_data, i); + snprintf(messageStr, sizeof(messageStr), "Processing list item index %d, item pointer: %p", i, (void*)item); + LogMsg(DEBUG, messageStr, fileName); if (TYPE(item) == PYTHON_NIL){ curr->bind_indicator_array[i] = SQL_NULL_DATA; + snprintf(messageStr, sizeof(messageStr), "List item index %d is PYTHON_NIL: bind_indicator_array[%d]=SQL_NULL_DATA", i, i); + LogMsg(DEBUG, messageStr, fileName); } else { (curr->ts_value + i)->year = PyDateTime_GET_YEAR(item); (curr->ts_value + i)->month = PyDateTime_GET_MONTH(item); @@ -6738,6 +8436,11 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py (curr->ts_value + i)->second = PyDateTime_DATE_GET_SECOND(item); (curr->ts_value + i)->fraction = PyDateTime_DATE_GET_MICROSECOND(item) * 1000; curr->bind_indicator_array[i] = SQL_NTS; + snprintf(messageStr, sizeof(messageStr), "List item index %d: year=%d, month=%d, day=%d, hour=%d, minute=%d, second=%d, fraction=%d, bind_indicator_array[%d]=SQL_NTS", + i, (curr->ts_value + i)->year, (curr->ts_value + i)->month, (curr->ts_value + i)->day, + (curr->ts_value + i)->hour, (curr->ts_value + i)->minute, (curr->ts_value + i)->second, + (curr->ts_value + i)->fraction, i); + LogMsg(DEBUG, messageStr, fileName); } } @@ -6746,6 +8449,9 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->param_type, SQL_C_TYPE_TIMESTAMP, curr->data_type, curr->param_size, curr->scale, curr->ts_value, curr->ivalue, &curr->bind_indicator_array[0]); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter for PYTHON_LIST with parameters: hstmt=%p, param_num=%d, param_type=%d, data_type=%d, param_size=%d, scale=%d, ts_value=%p, ivalue=%d, bind_indicator_array=%p and returned rc=%d", + (void*)stmt_res->hstmt, curr->param_num, curr->param_type, curr->data_type, curr->param_size, curr->scale, (void*)curr->ts_value, curr->ivalue, (void*)curr->bind_indicator_array, rc); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -6757,37 +8463,59 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py curr->ts_value->minute = PyDateTime_DATE_GET_MINUTE(bind_data); curr->ts_value->second = PyDateTime_DATE_GET_SECOND(bind_data); curr->ts_value->fraction = PyDateTime_DATE_GET_MICROSECOND(bind_data) * 1000; - + snprintf(messageStr, sizeof(messageStr), "Binding scalar value: year=%d, month=%d, day=%d, hour=%d, minute=%d, second=%d, fraction=%d", + curr->ts_value->year, curr->ts_value->month, curr->ts_value->day, + curr->ts_value->hour, curr->ts_value->minute, curr->ts_value->second, + curr->ts_value->fraction); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_TYPE_TIMESTAMP, curr->data_type, curr->param_size, curr->scale, curr->ts_value, curr->ivalue, &(curr->bind_indicator)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter for scalar value with parameters: hstmt=%p, param_num=%d, param_type=%d, data_type=%d, param_size=%d, scale=%d, ts_value=%p, ivalue=%d, bind_indicator=%p and returned rc=%d", + (void*)stmt_res->hstmt, curr->param_num, curr->param_type, curr->data_type, curr->param_size, curr->scale, + (void*)curr->ts_value, curr->ivalue, (void*)&(curr->bind_indicator), rc); + LogMsg(DEBUG, messageStr, fileName); } break; case PYTHON_NIL: + snprintf(messageStr, sizeof(messageStr), "Handling PYTHON_NIL case. Current data_type=%d", curr->data_type); + LogMsg(DEBUG, messageStr, fileName); if(TYPE(bind_data) == PYTHON_LIST){ Py_ssize_t n = PyList_Size(bind_data); + snprintf(messageStr, sizeof(messageStr), "PYTHON_LIST detected with size: %zd", n); + LogMsg(DEBUG, messageStr, fileName); curr->bind_indicator_array = (SQLINTEGER *) ALLOC_N(SQLINTEGER, n); for (i = 0; i < n; i++) { curr->bind_indicator_array[i] = SQL_NULL_DATA; + snprintf(messageStr, sizeof(messageStr), "List item index %d set to SQL_NULL_DATA", i); + LogMsg(DEBUG, messageStr, fileName); } Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_DEFAULT, curr->data_type, curr->param_size, curr->scale, curr->ivalueArray, 0, &curr->bind_indicator_array[0]); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter for PYTHON_LIST with parameters: hstmt=%p, param_num=%d, param_type=%d, data_type=%d, param_size=%d, scale=%d, ivalueArray=%p, bind_indicator_array=%p and returned rc=%d", + (void*)stmt_res->hstmt, curr->param_num, curr->param_type, curr->data_type, curr->param_size, curr->scale, + (void*)curr->ivalueArray, (void*)curr->bind_indicator_array, rc); + LogMsg(DEBUG, messageStr, fileName); } else { curr->ivalue = SQL_NULL_DATA; - + snprintf(messageStr, sizeof(messageStr), "Binding scalar value as SQL_NULL_DATA"); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, SQL_C_DEFAULT, curr->data_type, curr->param_size, curr->scale, &curr->ivalue, 0, (SQLLEN *)&(curr->ivalue)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLBindParameter for scalar PYTHON_NIL with parameters: hstmt=%p, param_num=%d, param_type=%d, SQL_C_DEFAULT, data_type=%d, param_size=%d, scale=%d, ivalue=%d and returned rc=%d", + (void *)stmt_res->hstmt, curr->param_num, curr->param_type, curr->data_type, curr->param_size, curr->scale, curr->ivalue, rc); + LogMsg(DEBUG, messageStr, fileName); } if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { @@ -6798,8 +8526,10 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py break; default: + LogMsg(ERROR, "Unhandled case in _python_ibm_db_bind_data(), default case", fileName); return SQL_ERROR; } + LogMsg(INFO, "exit _python_ibm_db_bind_data()", fileName); return rc; } @@ -6807,6 +8537,7 @@ static int _python_ibm_db_bind_data( stmt_handle *stmt_res, param_node *curr, Py */ static int _python_ibm_db_execute_helper2(stmt_handle *stmt_res, PyObject *data, int bind_cmp_list, int bind_params) { + LogMsg(INFO, "entry _python_ibm_db_execute_helper2()", fileName); int rc = SQL_SUCCESS; param_node *curr = NULL; /* To traverse the list */ PyObject *bind_data; /* Data value from symbol table */ @@ -6818,7 +8549,9 @@ static int _python_ibm_db_execute_helper2(stmt_handle *stmt_res, PyObject *data, SQLUINTEGER precision; SQLSMALLINT scale; SQLSMALLINT nullable; - + snprintf(messageStr, sizeof(messageStr),"Parameters: stmt_res->hstmt: %p, data: %p, bind_cmp_list: %d, bind_params: %d", + (SQLHSTMT)stmt_res->hstmt, data, bind_cmp_list, bind_params); + LogMsg(DEBUG, messageStr, fileName); /* This variable means that we bind the complete list of params cached */ /* The values used are fetched from the active symbol table */ /* TODO: Enhance this part to check for stmt_res->file_param */ @@ -6827,7 +8560,8 @@ static int _python_ibm_db_execute_helper2(stmt_handle *stmt_res, PyObject *data, /* Bind the complete list sequentially */ /* Used when no parameters array is passed in */ curr = stmt_res->head_cache_list; - + snprintf(messageStr, sizeof(messageStr), "Binding complete list. Initial node: %p", curr); + LogMsg(DEBUG, messageStr, fileName); while (curr != NULL ) { /* Fetch data from symbol table */ if (curr->param_type == PARAM_FILE) @@ -6835,35 +8569,47 @@ static int _python_ibm_db_execute_helper2(stmt_handle *stmt_res, PyObject *data, else { bind_data = curr->var_pyvalue; } + snprintf(messageStr, sizeof(messageStr), "Processing node: %p, param_type: %d, bind_data: %p", + curr, curr->param_type, bind_data); + LogMsg(DEBUG, messageStr, fileName); if (bind_data == NULL) return -1; rc = _python_ibm_db_bind_data( stmt_res, curr, bind_data); + snprintf(messageStr, sizeof(messageStr), "Called _python_ibm_db_bind_data with stmt_res: %p, curr: %p, bind_data: %p and returned rc: %d", stmt_res, curr, bind_data, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { sprintf(error, "Binding Error 1: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return rc; } curr = curr->next; } + LogMsg(INFO, "exit _python_ibm_db_execute_helper2()", fileName); return 0; } else { /* Bind only the data value passed in to the Current Node */ if ( data != NULL ) { + snprintf(messageStr, sizeof(messageStr), "data provided: %p", data); + LogMsg(DEBUG, messageStr, fileName); if ( bind_params ) { /* This condition applies if the parameter has not been * bound using ibm_db.bind_param. Need to describe the * parameter and then bind it. */ param_no = ++stmt_res->num_params; - + snprintf(messageStr, sizeof(messageStr), "Describing param with param_no: %d", param_no); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLDescribeParam((SQLHSTMT)stmt_res->hstmt, param_no, (SQLSMALLINT*)&data_type, &precision, (SQLSMALLINT*)&scale, (SQLSMALLINT*)&nullable); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "Called SQLDescribeParam with hstmt: %p, param_no: %d, data_type: %p, precision: %p, scale: %p, nullable: %p and returned rc: %d", + (SQLHSTMT)stmt_res->hstmt, param_no, (SQLSMALLINT*)&data_type, &precision, (SQLSMALLINT*)&scale, (SQLSMALLINT*)&nullable, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, @@ -6873,15 +8619,22 @@ static int _python_ibm_db_execute_helper2(stmt_handle *stmt_res, PyObject *data, if ( rc == SQL_ERROR ) { sprintf(error, "Describe Param Failed: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return rc; } curr = build_list(stmt_res, param_no, data_type, precision, scale, nullable); + snprintf(messageStr, sizeof(messageStr), "Built list with param_no: %d, data_type: %d, precision: %u, scale: %d, nullable: %d", + param_no, data_type, precision, scale, nullable); + LogMsg(DEBUG, messageStr, fileName); rc = _python_ibm_db_bind_data( stmt_res, curr, data); + snprintf(messageStr, sizeof(messageStr), "Called _python_ibm_db_bind_data with stmt_res: %p, curr: %p, data: %p and returned rc: %d", stmt_res, curr, data, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { sprintf(error, "Binding Error 2: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return rc; } @@ -6890,20 +8643,27 @@ static int _python_ibm_db_execute_helper2(stmt_handle *stmt_res, PyObject *data, * ibm_db.execute(), if params have been bound. */ curr = stmt_res->current_node; + snprintf(messageStr, sizeof(messageStr), "Binding to current node. Current node: %p", curr); + LogMsg(DEBUG, messageStr, fileName); if ( curr != NULL ) { rc = _python_ibm_db_bind_data( stmt_res, curr, data); + snprintf(messageStr, sizeof(messageStr), "Called _python_ibm_db_bind_data with stmt_res: %p, curr: %p, data: %p and returned rc: %d", stmt_res, curr, data, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { sprintf(error, "Binding Error 2: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return rc; } stmt_res->current_node = curr->next; } } + LogMsg(INFO, "exit _python_ibm_db_execute_helper2()", fileName); return rc; } } + LogMsg(INFO, "exit _python_ibm_db_execute_helper2()", fileName); return rc; } @@ -6913,11 +8673,15 @@ static int _python_ibm_db_execute_helper2(stmt_handle *stmt_res, PyObject *data, */ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject *parameters_tuple) { + LogMsg(INFO, "entry _python_ibm_db_execute_helper1()", fileName); int rc, numOpts, i, bind_params = 0; SQLSMALLINT num = 0; SQLPOINTER valuePtr; PyObject *data; char error[DB2_MAX_ERR_MSG_LEN +50]; + snprintf(messageStr, sizeof(messageStr), "stmt_res: %p, parameters_tuple: %p, bind_params: %d", + (void *)stmt_res, (void *)parameters_tuple, bind_params); + LogMsg(DEBUG, messageStr, fileName); /* Free any cursors that might have been allocated in a previous call to * SQLExecute */ @@ -6931,7 +8695,9 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject Py_BEGIN_ALLOW_THREADS; rc = SQLNumParams((SQLHSTMT)stmt_res->hstmt, (SQLSMALLINT*)&num); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLNumParams called with hstmt: %p, num: %p, and returned rc: %d", + (SQLHSTMT)stmt_res->hstmt, (SQLSMALLINT*)&num, rc); + LogMsg(DEBUG, messageStr, fileName); if ( num != 0 ) { /* Parameter Handling */ if ( !NIL_P(parameters_tuple) ) { @@ -6942,16 +8708,20 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject } if (!PyTuple_Check(parameters_tuple)) { + LogMsg(EXCEPTION, "Param is not a tuple", fileName); PyErr_SetString(PyExc_Exception, "Param is not a tuple"); return NULL; } numOpts = PyTuple_Size(parameters_tuple); - + snprintf(messageStr, sizeof(messageStr),"parameters_tuple: %p, numOpts: %d, num: %d", + (void *)parameters_tuple, numOpts, num); + LogMsg(DEBUG, messageStr, fileName); if (numOpts > num) { /* More are passed in -- Warning - Use the max number present */ sprintf(error, "%d params bound not matching %d required", numOpts, num); + LogMsg(WARNING, error, fileName); PyErr_SetString(PyExc_Exception, error); numOpts = stmt_res->num_params; } else if (numOpts < num) { @@ -6960,6 +8730,7 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject */ sprintf(error, "%d params bound not matching %d required", numOpts, num); + LogMsg(EXCEPTION, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } @@ -6967,15 +8738,21 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject for ( i = 0; i < numOpts; i++) { /* Bind values from the parameters_tuple to params */ data = PyTuple_GetItem(parameters_tuple, i); - + snprintf(messageStr, sizeof(messageStr), + "Binding parameter %d with data: %p", i, (void *)data); + LogMsg(DEBUG, messageStr, fileName); /* The 0 denotes that you work only with the current node. * The 4th argument specifies whether the data passed in * has been described. So we need to call SQLDescribeParam * before binding depending on this. */ rc = _python_ibm_db_execute_helper2(stmt_res, data, 0, bind_params); + snprintf(messageStr, sizeof(messageStr), "_python_ibm_db_execute_helper2 called with stmt_res: %p, data: %p, bind_params: %d, returned rc: %d", + (void *)stmt_res, (void *)data, bind_params, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR) { sprintf(error, "Binding Error: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } @@ -6986,17 +8763,20 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject /* More parameters than we expected */ sprintf(error, "%d params bound not matching %d required", stmt_res->num_params, num); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); } else if ( num < stmt_res->num_params ) { /* Fewer parameters than we expected */ sprintf(error, "%d params bound not matching %d required", stmt_res->num_params, num); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } /* Param cache node list is empty -- No params bound */ if ( stmt_res->head_cache_list == NULL ) { + LogMsg(EXCEPTION, "Parameters not bound", fileName); PyErr_SetString(PyExc_Exception, "Parameters not bound"); return NULL; } else { @@ -7004,8 +8784,12 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject * And bind sequentially */ rc = _python_ibm_db_execute_helper2(stmt_res, NULL, 1, 0); + snprintf(messageStr, sizeof(messageStr), "_python_ibm_db_execute_helper2 called with stmt_res: %p, data: NULL, bind_params: 0, and returned rc: %d", + (void *)stmt_res, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { sprintf(error, "Binding Error 3: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } @@ -7018,7 +8802,9 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject Py_BEGIN_ALLOW_THREADS; rc = SQLExecute((SQLHSTMT)stmt_res->hstmt); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr),"SQLExecute called with hstmt: %p, and returned rc: %d", + (SQLHSTMT)stmt_res->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, @@ -7030,6 +8816,7 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject PyErr_SetString(PyExc_Exception, error); return NULL; } + LogMsg(INFO, "exit _python_ibm_db_execute_helper1()", fileName); Py_INCREF(Py_True); return Py_True; } @@ -7038,6 +8825,9 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject Py_BEGIN_ALLOW_THREADS; rc = SQLExecute((SQLHSTMT)stmt_res->hstmt); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr),"SQLExecute called with hstmt: %p, and returned rc: %d", + (SQLHSTMT)stmt_res->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, @@ -7052,16 +8842,25 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject Py_BEGIN_ALLOW_THREADS; rc = SQLParamData((SQLHSTMT)stmt_res->hstmt, (SQLPOINTER *)&valuePtr); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLParamData called with hstmt: %p, valuePtr: %p, and returned rc: %d", + (SQLHSTMT)stmt_res->hstmt, (void *)valuePtr, rc); + LogMsg(DEBUG, messageStr, fileName); while ( rc == SQL_NEED_DATA ) { /* passing data value for a parameter */ if ( !NIL_P(((param_node*)valuePtr)->svalue)) { Py_BEGIN_ALLOW_THREADS; rc = SQLPutData((SQLHSTMT)stmt_res->hstmt, (SQLPOINTER)(((param_node*)valuePtr)->svalue), ((param_node*)valuePtr)->ivalue); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLPutData called with hstmt: %p, svalue: %p, ivalue: %d, and returned rc: %d", + (SQLHSTMT)stmt_res->hstmt, (void *)(((param_node *)valuePtr)->svalue), ((param_node *)valuePtr)->ivalue, rc); + LogMsg(DEBUG, messageStr, fileName); } else { Py_BEGIN_ALLOW_THREADS; rc = SQLPutData((SQLHSTMT)stmt_res->hstmt, (SQLPOINTER)(((param_node*)valuePtr)->uvalue), ((param_node*)valuePtr)->ivalue); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLPutData called with hstmt: %p, uvalue: %p, ivalue: %d, and returned rc: %d", + (SQLHSTMT)stmt_res->hstmt, (void *)(((param_node *)valuePtr)->uvalue), ((param_node *)valuePtr)->ivalue, rc); + LogMsg(DEBUG, messageStr, fileName); } if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { @@ -7079,6 +8878,9 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject Py_BEGIN_ALLOW_THREADS; rc = SQLParamData((SQLHSTMT)stmt_res->hstmt, (SQLPOINTER *)&valuePtr); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLParamData called with hstmt: %p, valuePtr: %p, and returned rc: %d", + (SQLHSTMT)stmt_res->hstmt, (void *)valuePtr, rc); + LogMsg(DEBUG, messageStr, fileName); } if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { @@ -7100,9 +8902,11 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject } if ( rc != SQL_ERROR ) { + LogMsg(INFO, "exit _python_ibm_db_execute_helper1()", fileName); Py_INCREF(Py_True); return Py_True; } + LogMsg(INFO, "exit _python_ibm_db_execute_helper1()", fileName); return NULL; } @@ -7141,28 +8945,41 @@ static PyObject *_python_ibm_db_execute_helper1(stmt_handle *stmt_res, PyObject */ static PyObject *ibm_db_execute(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry execute()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; PyObject *parameters_tuple = NULL; stmt_handle *stmt_res; - if (!PyArg_ParseTuple(args, "O|O", &py_stmt_res, ¶meters_tuple)) + if (!PyArg_ParseTuple(args, "O|O", &py_stmt_res, ¶meters_tuple)){ + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, parameters_tuple=%p", py_stmt_res, parameters_tuple); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_stmt_res)) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } + LogMsg(INFO, "Calling and returning _python_ibm_db_execute_helper1", fileName); + LogMsg(INFO, "exit execute()", fileName); return _python_ibm_db_execute_helper1(stmt_res, parameters_tuple); } else { + LogMsg(EXCEPTION, "Supplied parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } - } - /*!# ibm_db.conn_errormsg * * ===Description @@ -7191,6 +9008,10 @@ static PyObject *ibm_db_execute(PyObject *self, PyObject *args) */ static PyObject *ibm_db_conn_errormsg(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry conn_errormsg()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); conn_handle *conn_res = NULL; PyObject *py_conn_res = NULL; PyObject *retVal = NULL; @@ -7199,39 +9020,64 @@ static PyObject *ibm_db_conn_errormsg(PyObject *self, PyObject *args) * strings */ - if (!PyArg_ParseTuple(args, "|O", &py_conn_res)) + if (!PyArg_ParseTuple(args, "|O", &py_conn_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p", py_conn_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); } return_str = ALLOC_N(char, DB2_MAX_ERR_MSG_LEN); + snprintf(messageStr, sizeof(messageStr), "Allocated return_str: %p, size: %d", return_str, DB2_MAX_ERR_MSG_LEN); + LogMsg(DEBUG, messageStr, fileName); memset(return_str, 0, DB2_MAX_ERR_MSG_LEN); + LogMsg(DEBUG, "Initialized return_str with zeros", fileName); _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, -1, 0, return_str, DB2_ERRMSG, conn_res->errormsg_recno_tracker); - if(conn_res->errormsg_recno_tracker - conn_res->error_recno_tracker >= 1) - conn_res->error_recno_tracker = conn_res->errormsg_recno_tracker; + snprintf(messageStr, sizeof(messageStr), "SQL errors checked. return_str: %s", return_str); + LogMsg(DEBUG, messageStr, fileName); + if(conn_res->errormsg_recno_tracker - conn_res->error_recno_tracker >= 1) { + conn_res->error_recno_tracker = conn_res->errormsg_recno_tracker; + LogMsg(DEBUG, "Updated error_recno_tracker to match errormsg_recno_tracker", fileName); + } conn_res->errormsg_recno_tracker++; + snprintf(messageStr, sizeof(messageStr), "Updated error_recno_tracker: %d, errormsg_recno_tracker: %d", conn_res->error_recno_tracker, conn_res->errormsg_recno_tracker); + LogMsg(DEBUG, messageStr, fileName); retVal = StringOBJ_FromASCII(return_str); if(return_str != NULL) { PyMem_Del(return_str); return_str = NULL; } + snprintf(messageStr, sizeof(messageStr), "Created return value: %p", retVal); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit conn_errormsg()", fileName); return retVal; } else { + PyObject *defaultErrorMsg = StringOBJ_FromASCII(IBM_DB_G(__python_conn_err_msg)); + snprintf(messageStr, sizeof(messageStr), "No connection object provided. Returning default error message: %s", PyUnicode_AsUTF8(defaultErrorMsg)); + LogMsg(INFO, messageStr, fileName); + LogMsg(INFO, "exit conn_errormsg()", fileName); return StringOBJ_FromASCII(IBM_DB_G(__python_conn_err_msg)); } } @@ -7263,6 +9109,10 @@ static PyObject *ibm_db_conn_errormsg(PyObject *self, PyObject *args) */ static PyObject *ibm_db_conn_warn(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry conn_warn()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); conn_handle *conn_res = NULL; PyObject *py_conn_res = NULL; PyObject *retVal = NULL; @@ -7270,15 +9120,21 @@ static PyObject *ibm_db_conn_errormsg(PyObject *self, PyObject *args) * _python_ibm_db_check_sql_errors to return warning * strings */ - if (!PyArg_ParseTuple(args, "|O", &py_conn_res)) + if (!PyArg_ParseTuple(args, "|O", &py_conn_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p", py_conn_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res=%p", conn_res); + LogMsg(DEBUG, messageStr, fileName); } return_str = ALLOC_N(char, DB2_MAX_ERR_MSG_LEN); PyErr_Clear(); @@ -7289,16 +9145,24 @@ static PyObject *ibm_db_conn_errormsg(PyObject *self, PyObject *args) conn_res->error_recno_tracker); if (conn_res->error_recno_tracker-conn_res->errormsg_recno_tracker >= 1) { conn_res->errormsg_recno_tracker = conn_res->error_recno_tracker; + snprintf(messageStr, sizeof(messageStr), "Updated errormsg_recno_tracker to %d", conn_res->errormsg_recno_tracker); + LogMsg(DEBUG, messageStr, fileName); } conn_res->error_recno_tracker++; - retVal = StringOBJ_FromASCII( return_str ); if( return_str != NULL ) { PyMem_Del( return_str); return_str = NULL; } + snprintf(messageStr, sizeof(messageStr), "Returning warning message: %s", return_str); + LogMsg(INFO, messageStr, fileName); + LogMsg(INFO, "exit conn_warn()", fileName); return retVal; } else { + const char *default_warning_msg = IBM_DB_G(__python_conn_warn_msg); + snprintf(messageStr, sizeof(messageStr), "No connection object provided, returning default warning message: %s", default_warning_msg); + LogMsg(INFO, messageStr, fileName); + LogMsg(INFO, "exit conn_warn()", fileName); return StringOBJ_FromASCII(IBM_DB_G(__python_conn_warn_msg)); } } @@ -7327,6 +9191,10 @@ static PyObject *ibm_db_conn_errormsg(PyObject *self, PyObject *args) */ static PyObject *ibm_db_stmt_warn(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry stmt_warn()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); stmt_handle *stmt_res = NULL; PyObject *py_stmt_res = NULL; PyObject *retVal = NULL; @@ -7335,34 +9203,54 @@ static PyObject *ibm_db_stmt_warn(PyObject *self, PyObject *args) * strings */ - if (!PyArg_ParseTuple(args, "|O", &py_stmt_res)) + if (!PyArg_ParseTuple(args, "|O", &py_stmt_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p", py_stmt_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_stmt_res)) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res=%p", stmt_res); + LogMsg(DEBUG, messageStr, fileName); } return_str = ALLOC_N(char, DB2_MAX_ERR_MSG_LEN); memset(return_str, 0, DB2_MAX_ERR_MSG_LEN); - + snprintf(messageStr, sizeof(messageStr), "Calling _python_ibm_db_check_sql_errors with parameters: " + "hstmt=%p, handle_type=%d, recno_tracker=%d", + stmt_res->hstmt, SQL_HANDLE_STMT, stmt_res->errormsg_recno_tracker); + LogMsg(DEBUG, messageStr, fileName); _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, 1, 0, return_str, DB2_WARNMSG, stmt_res->errormsg_recno_tracker); - if(stmt_res->errormsg_recno_tracker - stmt_res->error_recno_tracker >= 1) + snprintf(messageStr, sizeof(messageStr), "Returned warning message: %s", return_str); + LogMsg(DEBUG, messageStr, fileName); + if(stmt_res->errormsg_recno_tracker - stmt_res->error_recno_tracker >= 1) { stmt_res->error_recno_tracker = stmt_res->errormsg_recno_tracker; + } stmt_res->errormsg_recno_tracker++; + snprintf(messageStr, sizeof(messageStr), "Updated error_recno_tracker=%d, errormsg_recno_tracker=%d", + stmt_res->error_recno_tracker, stmt_res->errormsg_recno_tracker); + LogMsg(DEBUG, messageStr, fileName); retVal = StringOBJ_FromASCII(return_str); if(return_str != NULL) { PyMem_Del(return_str); return_str = NULL; } + LogMsg(INFO, "exit stmt_warn()", fileName); return retVal; } else { + const char *default_warning_msg = IBM_DB_G(__python_stmt_warn_msg); + snprintf(messageStr, sizeof(messageStr), "No valid statement handle. Returning default warning message: %s", default_warning_msg); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit stmt_warn()", fileName); return StringOBJ_FromASCII(IBM_DB_G(__python_stmt_warn_msg)); } } @@ -7391,6 +9279,10 @@ static PyObject *ibm_db_stmt_warn(PyObject *self, PyObject *args) */ static PyObject *ibm_db_stmt_errormsg(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry stmt_errormsg()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); stmt_handle *stmt_res = NULL; PyObject *py_stmt_res = NULL; PyObject *retVal = NULL; @@ -7399,34 +9291,56 @@ static PyObject *ibm_db_stmt_errormsg(PyObject *self, PyObject *args) * strings */ - if (!PyArg_ParseTuple(args, "|O", &py_stmt_res)) + if (!PyArg_ParseTuple(args, "|O", &py_stmt_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p", py_stmt_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_stmt_res)) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } return_str = ALLOC_N(char, DB2_MAX_ERR_MSG_LEN); + snprintf(messageStr, sizeof(messageStr), "Allocated return_str: %p, size: %d", return_str, DB2_MAX_ERR_MSG_LEN); + LogMsg(DEBUG, messageStr, fileName); memset(return_str, 0, DB2_MAX_ERR_MSG_LEN); + LogMsg(DEBUG, "Initialized return_str with zeros", fileName); _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, -1, 0, return_str, DB2_ERRMSG, stmt_res->errormsg_recno_tracker); - if(stmt_res->errormsg_recno_tracker - stmt_res->error_recno_tracker >= 1) + snprintf(messageStr, sizeof(messageStr), "SQL errors checked. return_str: %s", return_str); + LogMsg(DEBUG, messageStr, fileName); + if(stmt_res->errormsg_recno_tracker - stmt_res->error_recno_tracker >= 1) { + LogMsg(DEBUG, "Updated error_recno_tracker to match errormsg_recno_tracker", fileName); stmt_res->error_recno_tracker = stmt_res->errormsg_recno_tracker; + } stmt_res->errormsg_recno_tracker++; + snprintf(messageStr, sizeof(messageStr), "Updated error_recno_tracker: %d, errormsg_recno_tracker: %d", stmt_res->error_recno_tracker, stmt_res->errormsg_recno_tracker); + LogMsg(DEBUG, messageStr, fileName); retVal = StringOBJ_FromStr(return_str); if(return_str != NULL) { PyMem_Del(return_str); return_str = NULL; } + snprintf(messageStr, sizeof(messageStr), "Created return value: %p", retVal); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit stmt_errormsg()", fileName); return retVal; } else { + PyObject *defaultErrorMsg = StringOBJ_FromASCII(IBM_DB_G(__python_stmt_err_msg)); + snprintf(messageStr, sizeof(messageStr), "No statement object provided. Returning default error message: %s", PyUnicode_AsUTF8(defaultErrorMsg)); + LogMsg(INFO, messageStr, fileName); + LogMsg(INFO, "exit stmt_errormsg()", fileName); return StringOBJ_FromStr(IBM_DB_G(__python_stmt_err_msg)); } } @@ -7463,6 +9377,10 @@ static PyObject *ibm_db_stmt_errormsg(PyObject *self, PyObject *args) */ static PyObject *ibm_db_conn_error(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry conn_error()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); conn_handle *conn_res = NULL; PyObject *py_conn_res = NULL; PyObject *retVal = NULL; @@ -7470,35 +9388,58 @@ static PyObject *ibm_db_conn_error(PyObject *self, PyObject *args) * _python_ibm_db_check_sql_errors to return err * strings */ - if (!PyArg_ParseTuple(args, "|O", &py_conn_res)) + if (!PyArg_ParseTuple(args, "|O", &py_conn_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, ", py_conn_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } return_str = ALLOC_N(char, SQL_SQLSTATE_SIZE + 1); + snprintf(messageStr, sizeof(messageStr), "Allocated return_str: %p, size: %d", return_str, SQL_SQLSTATE_SIZE + 1); + LogMsg(DEBUG, messageStr, fileName); memset(return_str, 0, SQL_SQLSTATE_SIZE + 1); + LogMsg(DEBUG, "Initialized return_str with zeros", fileName); _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, -1, 0, return_str, DB2_ERR, conn_res->error_recno_tracker); + snprintf(messageStr, sizeof(messageStr), "SQL errors checked. return_str: %s", return_str); + LogMsg(DEBUG, messageStr, fileName); if (conn_res->error_recno_tracker-conn_res->errormsg_recno_tracker >= 1) { + LogMsg(DEBUG, "Updating errormsg_recno_tracker", fileName); conn_res->errormsg_recno_tracker = conn_res->error_recno_tracker; } conn_res->error_recno_tracker++; + snprintf(messageStr, sizeof(messageStr), "Updated error_recno_tracker: %d, errormsg_recno_tracker: %d", conn_res->error_recno_tracker, conn_res->errormsg_recno_tracker); + LogMsg(DEBUG, messageStr, fileName); retVal = StringOBJ_FromASCII(return_str); if(return_str != NULL) { PyMem_Del(return_str); return_str = NULL; } + snprintf(messageStr, sizeof(messageStr), "Created return value: %p", retVal); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit conn_error()", fileName); return retVal; } else { + PyObject *defaultErrorState = StringOBJ_FromASCII(IBM_DB_G(__python_conn_err_state)); + snprintf(messageStr, sizeof(messageStr), "No connection object provided. Returning default error state: %s", PyUnicode_AsUTF8(defaultErrorState)); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit conn_error()", fileName); return StringOBJ_FromASCII(IBM_DB_G(__python_conn_err_state)); } } @@ -7531,6 +9472,10 @@ static PyObject *ibm_db_conn_error(PyObject *self, PyObject *args) */ static PyObject *ibm_db_stmt_error(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry stmt_error()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); stmt_handle *stmt_res = NULL; PyObject *py_stmt_res = NULL; PyObject *retVal = NULL; @@ -7539,36 +9484,57 @@ static PyObject *ibm_db_stmt_error(PyObject *self, PyObject *args) * strings */ - if (!PyArg_ParseTuple(args, "|O", &py_stmt_res)) + if (!PyArg_ParseTuple(args, "|O", &py_stmt_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, ", py_stmt_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_stmt_res)) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } return_str = ALLOC_N(char, DB2_MAX_ERR_MSG_LEN); + snprintf(messageStr, sizeof(messageStr), "Allocated return_str: %p, size: %d", return_str, DB2_MAX_ERR_MSG_LEN); + LogMsg(DEBUG, messageStr, fileName); memset(return_str, 0, DB2_MAX_ERR_MSG_LEN); + LogMsg(DEBUG, "Initialized return_str with zeros", fileName); _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, -1, 0, return_str, DB2_ERR, stmt_res->error_recno_tracker); + snprintf(messageStr, sizeof(messageStr), "SQL errors checked. return_str: %s", return_str); + LogMsg(DEBUG, messageStr, fileName); if (stmt_res->error_recno_tracker-stmt_res->errormsg_recno_tracker >= 1) { + LogMsg(DEBUG, "Updating errormsg_recno_tracker", fileName); stmt_res->errormsg_recno_tracker = stmt_res->error_recno_tracker; } stmt_res->error_recno_tracker++; + snprintf(messageStr, sizeof(messageStr), "Updated error_recno_tracker: %d, errormsg_recno_tracker: %d", stmt_res->error_recno_tracker, stmt_res->errormsg_recno_tracker); + LogMsg(DEBUG, messageStr, fileName); retVal = StringOBJ_FromASCII(return_str); if(return_str != NULL) { PyMem_Del(return_str); return_str = NULL; } + snprintf(messageStr, sizeof(messageStr), "Created return value: %p", retVal); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit stmt_error()", fileName); return retVal; } else { + PyObject *defaultErrorState = StringOBJ_FromASCII(IBM_DB_G(__python_stmt_err_state)); + snprintf(messageStr, sizeof(messageStr), "No Statement object provided. Returning default error state: %s", PyUnicode_AsUTF8(defaultErrorState)); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit conn_error()", fileName); return StringOBJ_FromASCII(IBM_DB_G(__python_stmt_err_state)); } } @@ -7598,20 +9564,30 @@ static PyObject *ibm_db_stmt_error(PyObject *self, PyObject *args) */ static PyObject *ibm_db_next_result(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry next_result()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; stmt_handle *stmt_res, *new_stmt_res = NULL; int rc = 0; SQLHANDLE new_hstmt; - if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) + if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p", py_stmt_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_stmt_res)) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } _python_ibm_db_clear_stmt_err_cache(); @@ -7620,6 +9596,9 @@ static PyObject *ibm_db_next_result(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; rc = SQLAllocHandle(SQL_HANDLE_STMT, stmt_res->hdbc, &new_hstmt); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLAllocHandle with parameters SQL_HANDLE_STMT, hdbc=%p, &new_hstmt=%p and returned rc=%d", + (void *)stmt_res->hdbc, (void *)new_hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); #endif if ( rc < SQL_SUCCESS ) { _python_ibm_db_check_sql_errors(stmt_res->hdbc, SQL_HANDLE_DBC, rc, 1, @@ -7631,8 +9610,12 @@ static PyObject *ibm_db_next_result(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; #ifdef __MVS__ rc = SQLMoreResults((SQLHSTMT)stmt_res->hstmt); + snprintf(messageStr, sizeof(messageStr), "Called SQLMoreResults with Parameter hstmt=%p and returned rc=%d", (void *)stmt_res->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); #else rc = SQLNextResult((SQLHSTMT)stmt_res->hstmt, (SQLHSTMT)new_hstmt); + snprintf(messageStr, sizeof(messageStr), "Called SQLNextResult with Parameter hstmt=%p, new_hstmt=%p and returned rc=%d", (void *)stmt_res->hstmt, (void *)new_hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); #endif Py_END_ALLOW_THREADS; @@ -7645,8 +9628,11 @@ static PyObject *ibm_db_next_result(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; SQLFreeHandle(SQL_HANDLE_STMT, new_hstmt); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLFreeHandle with parameters SQL_HANDLE_STMT, new_hstmt=%p and returned rc=%d",(void *)new_hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); #endif Py_INCREF(Py_False); + LogMsg(INFO, "exit next_result()", fileName); return Py_False; } @@ -7654,6 +9640,8 @@ static PyObject *ibm_db_next_result(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; SQLFreeStmt(stmt_res->hstmt, SQL_UNBIND); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "Called SQLFreeStmt with parameters hstmt=%p, SQL_UNBIND and returned rc=%d",(void *)stmt_res->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); #endif /* Initialize stmt resource members with default values. */ /* Parsing will update options if needed */ @@ -7684,9 +9672,10 @@ static PyObject *ibm_db_next_result(PyObject *self, PyObject *args) stmt_res->errormsg_recno_tracker = 1; new_stmt_res->row_data = NULL; - + LogMsg(INFO, "exit next_result()", fileName); return (PyObject *)new_stmt_res; } else { + LogMsg(ERROR, "Supplied parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } @@ -7715,27 +9704,38 @@ static PyObject *ibm_db_next_result(PyObject *self, PyObject *args) */ static PyObject *ibm_db_num_fields(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry num_fields()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; stmt_handle *stmt_res; int rc = 0; SQLSMALLINT indx = 0; char error[DB2_MAX_ERR_MSG_LEN +50]; - if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) + if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p", py_stmt_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_stmt_res)) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } Py_BEGIN_ALLOW_THREADS; rc = SQLNumResultCols((SQLHSTMT)stmt_res->hstmt, &indx); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLNumResultCols return code: %d, Number of columns: %d", rc, indx); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); @@ -7744,15 +9744,19 @@ static PyObject *ibm_db_num_fields(PyObject *self, PyObject *args) { sprintf(error, "SQLNumResultCols failed: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } + LogMsg(INFO, "exit num_fields()", fileName); return PyInt_FromLong(indx); } else { + LogMsg(ERROR, "Supplied parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } Py_INCREF(Py_False); + LogMsg(INFO, "exit num_fields()", fileName); return Py_False; } @@ -7792,37 +9796,53 @@ static PyObject *ibm_db_num_fields(PyObject *self, PyObject *args) */ static PyObject *ibm_db_num_rows(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry num_rows()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; stmt_handle *stmt_res; int rc = 0; SQLINTEGER count = 0; - char error[DB2_MAX_ERR_MSG_LEN + 50]; + char error[DB2_MAX_ERR_MSG_LEN +50]; - if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) + if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p", py_stmt_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_stmt_res)) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } Py_BEGIN_ALLOW_THREADS; rc = SQLRowCount((SQLHSTMT)stmt_res->hstmt, &count); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLRowCount return code: %d, count: %d", rc, count); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); sprintf(error, "SQLRowCount failed: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Row count retrieved: %d", count); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit num_rows()", fileName); return PyInt_FromLong(count); } else { + LogMsg(ERROR, "Supplied parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } @@ -7848,6 +9868,10 @@ static PyObject *ibm_db_num_rows(PyObject *self, PyObject *args) */ static PyObject *ibm_db_get_num_result(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry get_num_result()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; stmt_handle *stmt_res; int rc = 0; @@ -7855,20 +9879,27 @@ static PyObject *ibm_db_get_num_result(PyObject *self, PyObject *args) char error[DB2_MAX_ERR_MSG_LEN +50]; SQLSMALLINT strLenPtr; - if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) + if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p", py_stmt_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_stmt_res)) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valie. stmt_res=%p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } Py_BEGIN_ALLOW_THREADS; #ifdef __MVS__ /* z/OS DB2 ODBC only seems to have SQLGetDiagRec */ + LogMsg(DEBUG, "This system not have SQLGetDiagRec. rc set to SQL_SUCCESS", fileName); rc = SQL_SUCCESS; #else rc = SQLGetDiagField(SQL_HANDLE_STMT, stmt_res->hstmt, 0, @@ -7876,7 +9907,10 @@ static PyObject *ibm_db_get_num_result(PyObject *self, PyObject *args) &strLenPtr); #endif Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "Called SQLGetDiagField with parameters: HandleType=SQL_HANDLE_STMT, StatementHandle=%p, RecordNumber=0, DiagField=SQL_DIAG_CURSOR_ROW_COUNT, RowCountPointer=%p, DataType=SQL_IS_INTEGER, StringLengthPointer=%p and returned rc=%d, count=%d", + stmt_res->hstmt, &count, &strLenPtr, rc, count); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, SQL_HANDLE_STMT, @@ -7885,14 +9919,20 @@ static PyObject *ibm_db_get_num_result(PyObject *self, PyObject *args) if ( rc == SQL_ERROR ) { sprintf(error, "SQLGetDiagField failed: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Returning row count: %d", count); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit get_num_result()", fileName); return PyInt_FromLong(count); } else { + LogMsg(ERROR, "Supplied parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } + LogMsg(INFO, "exit get_num_result()", fileName); Py_INCREF(Py_False); return Py_False; } @@ -7901,28 +9941,60 @@ static PyObject *ibm_db_get_num_result(PyObject *self, PyObject *args) */ static int _python_ibm_db_get_column_by_name(stmt_handle *stmt_res, char *col_name, int col) { + LogMsg(INFO, "entry _python_ibm_db_get_column_by_name()", fileName); + snprintf(messageStr, sizeof(messageStr), + "stmt_res=%p, col_name=%s, col=%d", + (void *)stmt_res, col_name ? col_name : "NULL", col); + LogMsg(DEBUG, messageStr, fileName); int i; /* get column header info */ + snprintf(messageStr, sizeof(messageStr), "Checking column_info: column_info=%p, num_columns=%d", + (void *)stmt_res->column_info, stmt_res->num_columns); + LogMsg(DEBUG, messageStr, fileName); if ( stmt_res->column_info == NULL ) { + int result = _python_ibm_db_get_result_set_info(stmt_res); + snprintf(messageStr, sizeof(messageStr), + "Result of _python_ibm_db_get_result_set_info: %d", result); + LogMsg(DEBUG, messageStr, fileName); if (_python_ibm_db_get_result_set_info(stmt_res)<0) { + LogMsg(DEBUG, "Failed to get result set info", fileName); + LogMsg(INFO, "exit _python_ibm_db_get_column_by_name()", fileName); return -1; } } if ( col_name == NULL ) { + snprintf(messageStr, sizeof(messageStr), + "col_name is NULL, col=%d, num_columns=%d", col, stmt_res->num_columns); + LogMsg(DEBUG, messageStr, fileName); if ( col >= 0 && col < stmt_res->num_columns) { + snprintf(messageStr, sizeof(messageStr), "Returning col=%d", col); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit _python_ibm_db_get_column_by_name()", fileName); return col; } else { + LogMsg(DEBUG, "Invalid col index", fileName); + LogMsg(INFO, "exit _python_ibm_db_get_column_by_name()", fileName); return -1; } } /* should start from 0 */ + snprintf(messageStr, sizeof(messageStr), + "Searching for column name: col_name=%s", col_name); + LogMsg(DEBUG, messageStr, fileName); i = 0; while (i < stmt_res->num_columns) { + snprintf(messageStr, sizeof(messageStr), "Checking column %d: name=%s", i, stmt_res->column_info[i].name); + LogMsg(DEBUG, messageStr, fileName); if (strcmp((char*)stmt_res->column_info[i].name, col_name) == 0) { + snprintf(messageStr, sizeof(messageStr), "Found column: index=%d", i); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit _python_ibm_db_get_column_by_name()", fileName); return i; } i++; } + LogMsg(DEBUG, "Column not found", fileName); + LogMsg(INFO, "exit _python_ibm_db_get_column_by_name()", fileName); return -1; } @@ -7951,7 +10023,12 @@ static int _python_ibm_db_get_column_by_name(stmt_handle *stmt_res, char *col_na */ static PyObject *ibm_db_field_name(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry field_name()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *column = NULL; + PyObject *result = NULL; #if PY_MAJOR_VERSION >= 3 PyObject *col_name_py3_tmp = NULL; #endif @@ -7960,29 +10037,42 @@ static PyObject *ibm_db_field_name(PyObject *self, PyObject *args) char *col_name = NULL; int col = -1; - if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) + if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, column=%p", py_stmt_res, column); + LogMsg(DEBUG, messageStr, fileName); if (NIL_P(py_stmt_res) || (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType))) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if ( TYPE(column) == PYTHON_FIXNUM ) { - col = PyInt_AsLong(column); + col = PyLong_AsLong(column); + snprintf(messageStr, sizeof(messageStr), "Column index is an integer: %d", col); + LogMsg(DEBUG, messageStr, fileName); } else if (PyString_Check(column)) { #if PY_MAJOR_VERSION >= 3 col_name_py3_tmp = PyUnicode_AsASCIIString(column); if (col_name_py3_tmp == NULL) { + LogMsg(ERROR, "Failed to convert Unicode column name to ASCII", fileName); return NULL; } column = col_name_py3_tmp; #endif col_name = PyBytes_AsString(column); + snprintf(messageStr, sizeof(messageStr), "Column name is a string: %s", col_name); + LogMsg(DEBUG, messageStr, fileName); } else { /* Column argument has to be either an integer or string */ + LogMsg(ERROR, "Column argument has to be either an integer or string", fileName); + LogMsg(INFO, "exit field_name()", fileName); Py_RETURN_FALSE; } col = _python_ibm_db_get_column_by_name(stmt_res, col_name, col); @@ -7992,9 +10082,35 @@ static PyObject *ibm_db_field_name(PyObject *self, PyObject *args) } #endif if ( col < 0 ) { + LogMsg(DEBUG, "Column index not found", fileName); + LogMsg(INFO, "exit field_name()", fileName); Py_INCREF(Py_False); return Py_False; } +#ifdef _WIN32 + result = PyUnicode_DecodeLocale((char*)stmt_res->column_info[col].name,"surrogateescape"); +#else + result = PyUnicode_FromString((char*)stmt_res->column_info[col].name); +#endif + if (result) { + const char *result_str = NULL; + #if PY_MAJOR_VERSION >= 3 + result_str = PyUnicode_AsUTF8(result); + #else + result_str = PyString_AsString(result); + #endif + + if (result_str) { + snprintf(messageStr, sizeof(messageStr), "Successfully retrieved column name: %s", result_str); + LogMsg(DEBUG, messageStr, fileName); + } else { + LogMsg(ERROR, "Failed to convert result to UTF-8 string", fileName); + } + Py_DECREF(result); + } else { + LogMsg(ERROR, "Failed to create Unicode object from column name", fileName); + } + LogMsg(INFO, "exit field_name()", fileName); #ifdef _WIN32 return PyUnicode_DecodeLocale((char*)stmt_res->column_info[col].name,"surrogateescape"); #else @@ -8028,6 +10144,10 @@ static PyObject *ibm_db_field_name(PyObject *self, PyObject *args) */ static PyObject *ibm_db_field_display_size(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry field_display_size()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; PyObject *column = NULL; #if PY_MAJOR_VERSION >= 3 @@ -8039,38 +10159,58 @@ static PyObject *ibm_db_field_display_size(PyObject *self, PyObject *args) int rc; SQLINTEGER colDataDisplaySize; - if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) + if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, column=%p", py_stmt_res, column); + LogMsg(DEBUG, messageStr, fileName); if (NIL_P(py_stmt_res) || (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType))) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if ( TYPE(column) == PYTHON_FIXNUM ) { - col = PyInt_AsLong(column); + col = PyLong_AsLong(column); + snprintf(messageStr, sizeof(messageStr), "Column is an integer: col=%d", col); + LogMsg(DEBUG, messageStr, fileName); } else if (PyString_Check(column)) { #if PY_MAJOR_VERSION >= 3 col_name_py3_tmp = PyUnicode_AsASCIIString(column); if (col_name_py3_tmp == NULL) { + LogMsg(ERROR, "Failed to convert Unicode to ASCII", fileName); return NULL; } column = col_name_py3_tmp; + snprintf(messageStr, sizeof(messageStr), "Converted column to ASCII: %s", PyBytes_AsString(column)); + LogMsg(DEBUG, messageStr, fileName); #endif col_name = PyBytes_AsString(column); + snprintf(messageStr, sizeof(messageStr), "Column is a string: col_name=%s", col_name); + LogMsg(DEBUG, messageStr, fileName); } else { /* Column argument has to be either an integer or string */ + LogMsg(ERROR, "Column argument has to be either an integer or string", fileName); + LogMsg(INFO, "exit field_display_size()", fileName); Py_RETURN_FALSE; } col = _python_ibm_db_get_column_by_name(stmt_res, col_name, col); + snprintf(messageStr, sizeof(messageStr), "Column index after _python_ibm_db_get_column_by_name: %d", col); + LogMsg(DEBUG, messageStr, fileName); #if PY_MAJOR_VERSION >= 3 if ( col_name_py3_tmp != NULL ) { Py_XDECREF(col_name_py3_tmp); + LogMsg(DEBUG, "Cleaned up col_name_py3_tmp", fileName); } #endif if ( col < 0 ) { + LogMsg(ERROR, "Invalid column index", fileName); + LogMsg(INFO, "exit field_display_size()", fileName); Py_RETURN_FALSE; } @@ -8078,16 +10218,20 @@ static PyObject *ibm_db_field_display_size(PyObject *self, PyObject *args) rc = SQLColAttributes((SQLHSTMT)stmt_res->hstmt, (SQLSMALLINT)col+1, SQL_DESC_DISPLAY_SIZE, NULL, 0, NULL, &colDataDisplaySize); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLColAttributes return code: %d, colDataDisplaySize: %d", rc, colDataDisplaySize); + LogMsg(DEBUG, messageStr, fileName); if ( rc < SQL_SUCCESS || rc == SQL_SUCCESS_WITH_INFO ) { + LogMsg(ERROR, "SQLColAttributes failed", fileName); _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } if( rc < SQL_SUCCESS ) { Py_INCREF(Py_False); + LogMsg(INFO, "exit field_display_size()", fileName); return Py_False; } + LogMsg(INFO, "exit field_display_size()", fileName); return PyInt_FromLong(colDataDisplaySize); } /*!# ibm_db.field_nullable @@ -8114,6 +10258,10 @@ static PyObject *ibm_db_field_display_size(PyObject *self, PyObject *args) */ static PyObject *ibm_db_field_nullable(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry field_nullable()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; PyObject *column = NULL; #if PY_MAJOR_VERSION >= 3 @@ -8125,46 +10273,67 @@ static PyObject *ibm_db_field_nullable(PyObject *self, PyObject *args) int rc; SQLINTEGER nullableCol; - if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) + if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, column=%p", py_stmt_res, column); + LogMsg(DEBUG, messageStr, fileName); if (NIL_P(py_stmt_res) || (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType))) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res=%p", stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if ( TYPE(column) == PYTHON_FIXNUM ) { - col = PyInt_AsLong(column); + col = PyLong_AsLong(column); + snprintf(messageStr, sizeof(messageStr), "Column index parsed: col=%d", col); + LogMsg(DEBUG, messageStr, fileName); } else if (PyString_Check(column)) { #if PY_MAJOR_VERSION >= 3 col_name_py3_tmp = PyUnicode_AsASCIIString(column); if (col_name_py3_tmp == NULL) { + LogMsg(ERROR, "Failed to convert column name to ASCII", fileName); return NULL; } column = col_name_py3_tmp; #endif col_name = PyBytes_AsString(column); + snprintf(messageStr, sizeof(messageStr), "Column name parsed: col_name=%s", col_name); + LogMsg(DEBUG, messageStr, fileName); } else { /* Column argument has to be either an integer or string */ + LogMsg(INFO, "Invalid column argument. Must be an integer or string", fileName); Py_RETURN_FALSE; } + snprintf(messageStr, sizeof(messageStr), "Calling _python_ibm_db_get_column_by_name with parameters: stmt_res=%p, col_name=%s, col=%d", stmt_res, col_name, col); + LogMsg(DEBUG, messageStr, fileName); col = _python_ibm_db_get_column_by_name(stmt_res, col_name, col); + snprintf(messageStr, sizeof(messageStr), + "_python_ibm_db_get_column_by_name returned: col=%d", col); + LogMsg(DEBUG, messageStr, fileName); #if PY_MAJOR_VERSION >= 3 if ( col_name_py3_tmp != NULL ) { Py_XDECREF(col_name_py3_tmp); } #endif if ( col < 0 ) { - Py_RETURN_FALSE; + LogMsg(INFO, "Invalid column index.", fileName); + LogMsg(INFO, "exit field_nullable()", fileName); + Py_RETURN_FALSE; } Py_BEGIN_ALLOW_THREADS; rc = SQLColAttributes((SQLHSTMT)stmt_res->hstmt, (SQLSMALLINT)col+1, SQL_DESC_NULLABLE, NULL, 0, NULL, &nullableCol); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "Called SQLColAttributes with parameters: StatementHandle=%p, ColumnIndex=%d, and returned rc=%d, NullableCol=%d", + stmt_res->hstmt, col + 1, rc, nullableCol); + LogMsg(DEBUG, messageStr, fileName); if ( rc < SQL_SUCCESS ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); @@ -8177,8 +10346,12 @@ static PyObject *ibm_db_field_nullable(PyObject *self, PyObject *args) Py_RETURN_FALSE; } else if ( nullableCol == SQL_NULLABLE ) { + LogMsg(INFO, "Column is nullable.", fileName); + LogMsg(INFO, "exit field_nullable()", fileName); Py_RETURN_TRUE; } else { + LogMsg(INFO, "Column is not nullable.", fileName); + LogMsg(INFO, "exit field_nullable()", fileName); Py_RETURN_FALSE; } } @@ -8207,6 +10380,10 @@ static PyObject *ibm_db_field_nullable(PyObject *self, PyObject *args) */ static PyObject *ibm_db_field_num(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry field_num()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; PyObject *column = NULL; #if PY_MAJOR_VERSION >= 3 @@ -8216,29 +10393,41 @@ static PyObject *ibm_db_field_num(PyObject *self, PyObject *args) char *col_name = NULL; int col = -1; - if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) + if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, column=%p", py_stmt_res, column); + LogMsg(DEBUG, messageStr, fileName); if (NIL_P(py_stmt_res) || (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType))) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if ( TYPE(column) == PYTHON_FIXNUM ) { - col = PyInt_AsLong(column); + col = PyLong_AsLong(column); + snprintf(messageStr, sizeof(messageStr), "Column index is an integer: %d", col); + LogMsg(DEBUG, messageStr, fileName); } else if (PyString_Check(column)) { #if PY_MAJOR_VERSION >= 3 col_name_py3_tmp = PyUnicode_AsASCIIString(column); if (col_name_py3_tmp == NULL) { + LogMsg(ERROR, "Failed to convert Unicode column name to ASCII", fileName); return NULL; } column = col_name_py3_tmp; #endif col_name = PyBytes_AsString(column); + snprintf(messageStr, sizeof(messageStr), "Column name is a string: %s", col_name); + LogMsg(DEBUG, messageStr, fileName); } else { /* Column argument has to be either an integer or string */ + LogMsg(ERROR, "Column argument has to be either an integer or string", fileName); Py_RETURN_FALSE; } col = _python_ibm_db_get_column_by_name(stmt_res, col_name, col); @@ -8248,9 +10437,14 @@ static PyObject *ibm_db_field_num(PyObject *self, PyObject *args) } #endif if ( col < 0 ) { + LogMsg(DEBUG, "Column index not found", fileName); Py_INCREF(Py_False); + LogMsg(INFO, "exit field_num()", fileName); return Py_False; } + snprintf(messageStr, sizeof(messageStr), "The 0-indexed position of the specified column is: %ld", col); + LogMsg(INFO, messageStr, fileName); + LogMsg(INFO, "exit field_num()", fileName); return PyInt_FromLong(col); } @@ -8279,6 +10473,10 @@ static PyObject *ibm_db_field_num(PyObject *self, PyObject *args) */ static PyObject *ibm_db_field_precision(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry field_precision()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; PyObject *column = NULL; #if PY_MAJOR_VERSION >= 3 @@ -8288,29 +10486,42 @@ static PyObject *ibm_db_field_precision(PyObject *self, PyObject *args) char *col_name = NULL; int col = -1; - if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) + if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, column=%p", py_stmt_res, column); + LogMsg(DEBUG, messageStr, fileName); if (NIL_P(py_stmt_res) || (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType))) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if ( TYPE(column) == PYTHON_FIXNUM ) { - col = PyInt_AsLong(column); + col = PyLong_AsLong(column); + snprintf(messageStr, sizeof(messageStr), "Column index is an integer: %d", col); + LogMsg(DEBUG, messageStr, fileName); } else if (PyString_Check(column)) { #if PY_MAJOR_VERSION >= 3 col_name_py3_tmp = PyUnicode_AsASCIIString(column); if (col_name_py3_tmp == NULL) { + LogMsg(ERROR, "Failed to convert Unicode column name to ASCII", fileName); return NULL; } column = col_name_py3_tmp; #endif col_name = PyBytes_AsString(column); + snprintf(messageStr, sizeof(messageStr), "Column name is a string: %s", col_name); + LogMsg(DEBUG, messageStr, fileName); } else { /* Column argument has to be either an integer or string */ + LogMsg(ERROR, "Column argument has to be either an integer or string", fileName); + LogMsg(INFO, "exit field_precision()", fileName); Py_RETURN_FALSE; } col = _python_ibm_db_get_column_by_name(stmt_res, col_name, col); @@ -8319,11 +10530,17 @@ static PyObject *ibm_db_field_precision(PyObject *self, PyObject *args) Py_XDECREF(col_name_py3_tmp); } #endif + snprintf(messageStr, sizeof(messageStr), "Column index found: %d", col); + LogMsg(DEBUG, messageStr, fileName); if ( col < 0 ) { + LogMsg(DEBUG, "Column index not found", fileName); + LogMsg(INFO, "exit field_precision()", fileName); Py_RETURN_FALSE; } + snprintf(messageStr, sizeof(messageStr), "Successfully retrieved field precision: %ld", stmt_res->column_info[col].size); + LogMsg(INFO, messageStr, fileName); + LogMsg(INFO, "exit field_precision()", fileName); return PyInt_FromLong(stmt_res->column_info[col].size); - } /*!# ibm_db.field_scale @@ -8350,6 +10567,10 @@ static PyObject *ibm_db_field_precision(PyObject *self, PyObject *args) */ static PyObject *ibm_db_field_scale(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry field_scale()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; PyObject *column = NULL; #if PY_MAJOR_VERSION >= 3 @@ -8359,39 +10580,59 @@ static PyObject *ibm_db_field_scale(PyObject *self, PyObject *args) char *col_name = NULL; int col = -1; - if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) + if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, column=%p", py_stmt_res, column); + LogMsg(DEBUG, messageStr, fileName); if (NIL_P(py_stmt_res) || (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType))) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if ( TYPE(column) == PYTHON_FIXNUM ) { - col = PyInt_AsLong(column); + col = PyLong_AsLong(column); + snprintf(messageStr, sizeof(messageStr), "Column is an integer. col=%d", col); + LogMsg(DEBUG, messageStr, fileName); } else if (PyString_Check(column)) { #if PY_MAJOR_VERSION >= 3 col_name_py3_tmp = PyUnicode_AsASCIIString(column); if (col_name_py3_tmp == NULL) { + LogMsg(ERROR, "Failed to convert column name to ASCII string", fileName); return NULL; } column = col_name_py3_tmp; #endif col_name = PyBytes_AsString(column); + snprintf(messageStr, sizeof(messageStr), "Column is a string. col_name=%s", col_name); + LogMsg(DEBUG, messageStr, fileName); } else { /* Column argument has to be either an integer or string */ + LogMsg(ERROR, "Column argument must be an integer or string", fileName); Py_RETURN_FALSE; } col = _python_ibm_db_get_column_by_name(stmt_res, col_name, col); + snprintf(messageStr, sizeof(messageStr), "Column index obtained: col=%d", col); + LogMsg(DEBUG, messageStr, fileName); #if PY_MAJOR_VERSION >= 3 if ( col_name_py3_tmp != NULL ) { Py_XDECREF(col_name_py3_tmp); } #endif if ( col < 0 ) { + LogMsg(ERROR, "Column index is invalid", fileName); + LogMsg(INFO, "exit field_scale()", fileName); Py_RETURN_FALSE; } + long scale = stmt_res->column_info[col].scale; + snprintf(messageStr, sizeof(messageStr), "Column scale: %ld", scale); + LogMsg(INFO, messageStr, fileName); + LogMsg(INFO, "exit field_scale()", fileName); return PyInt_FromLong(stmt_res->column_info[col].scale); } @@ -8419,6 +10660,10 @@ static PyObject *ibm_db_field_scale(PyObject *self, PyObject *args) */ static PyObject *ibm_db_field_type(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry field_type()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; PyObject *column = NULL; #if PY_MAJOR_VERSION >= 3 @@ -8429,28 +10674,40 @@ static PyObject *ibm_db_field_type(PyObject *self, PyObject *args) char *str_val = NULL; int col = -1; - if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) + if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, column=%p", py_stmt_res, column); + LogMsg(DEBUG, messageStr, fileName); if (NIL_P(py_stmt_res) || (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType))) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if ( TYPE(column) == PYTHON_FIXNUM ) { - col = PyInt_AsLong(column); + col = PyLong_AsLong(column); + snprintf(messageStr, sizeof(messageStr), "Column is an integer: %d", col); + LogMsg(DEBUG, messageStr, fileName); } else if (PyString_Check(column)) { #if PY_MAJOR_VERSION >= 3 col_name_py3_tmp = PyUnicode_AsASCIIString(column); if (col_name_py3_tmp == NULL) { + LogMsg(ERROR, "Failed to convert column name to ASCII string", fileName); return NULL; } column = col_name_py3_tmp; #endif col_name = PyBytes_AsString(column); + snprintf(messageStr, sizeof(messageStr), "Column is a string: %s", col_name); + LogMsg(DEBUG, messageStr, fileName); } else { /* Column argument has to be either an integer or string */ + LogMsg(ERROR, "Column argument must be an integer or string", fileName); Py_RETURN_FALSE; } col = _python_ibm_db_get_column_by_name(stmt_res, col_name, col); @@ -8459,7 +10716,10 @@ static PyObject *ibm_db_field_type(PyObject *self, PyObject *args) Py_XDECREF(col_name_py3_tmp); } #endif + snprintf(messageStr, sizeof(messageStr), "Column index: %d", col); + LogMsg(DEBUG, messageStr, fileName); if ( col < 0 ) { + LogMsg(ERROR, "Column index is negative, column not found", fileName); Py_RETURN_FALSE; } switch (stmt_res->column_info[col].type) { @@ -8511,6 +10771,9 @@ static PyObject *ibm_db_field_type(PyObject *self, PyObject *args) str_val = "string"; break; } + snprintf(messageStr, sizeof(messageStr), "Determined column type: %s", str_val); + LogMsg(INFO, messageStr, fileName); + LogMsg(INFO, "exit field_type()", fileName); return StringOBJ_FromASCII(str_val); } @@ -8541,6 +10804,10 @@ static PyObject *ibm_db_field_type(PyObject *self, PyObject *args) */ static PyObject *ibm_db_field_width(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry field_width()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; PyObject *column = NULL; #if PY_MAJOR_VERSION >= 3 @@ -8552,28 +10819,40 @@ static PyObject *ibm_db_field_width(PyObject *self, PyObject *args) int rc; SQLINTEGER colDataSize; - if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) + if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, column=%p", py_stmt_res, column); + LogMsg(DEBUG, messageStr, fileName); if (NIL_P(py_stmt_res) || (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType))) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if ( TYPE(column) == PYTHON_FIXNUM ) { - col = PyInt_AsLong(column); + col = PyLong_AsLong(column); + snprintf(messageStr, sizeof(messageStr), "Column is an integer: %d", col); + LogMsg(DEBUG, messageStr, fileName); } else if (PyString_Check(column)) { #if PY_MAJOR_VERSION >= 3 col_name_py3_tmp = PyUnicode_AsASCIIString(column); if (col_name_py3_tmp == NULL) { + LogMsg(ERROR, "Failed to convert column name to ASCII string", fileName); return NULL; } column = col_name_py3_tmp; #endif col_name = PyBytes_AsString(column); + snprintf(messageStr, sizeof(messageStr), "Column is a string: %s", col_name); + LogMsg(DEBUG, messageStr, fileName); } else { /* Column argument has to be either an integer or string */ + LogMsg(ERROR, "Column argument must be an integer or string", fileName); Py_RETURN_FALSE; } col = _python_ibm_db_get_column_by_name(stmt_res, col_name, col); @@ -8582,7 +10861,10 @@ static PyObject *ibm_db_field_width(PyObject *self, PyObject *args) Py_XDECREF(col_name_py3_tmp); } #endif + snprintf(messageStr, sizeof(messageStr), "Column index: %d", col); + LogMsg(DEBUG, messageStr, fileName); if ( col < 0 ) { + LogMsg(ERROR, "Column index is negative, column not found", fileName); Py_RETURN_FALSE; } @@ -8590,13 +10872,19 @@ static PyObject *ibm_db_field_width(PyObject *self, PyObject *args) rc = SQLColAttributes((SQLHSTMT)stmt_res->hstmt, (SQLSMALLINT)col + 1, SQL_DESC_LENGTH, NULL, 0, NULL, &colDataSize); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "Called SQLColAttributes with parameters: stmt_res->hstmt=%p, col=%d, SQL_DESC_LENGTH=%d and returned: rc=%d, colDataSize=%ld", + (void *)stmt_res->hstmt, col + 1, SQL_DESC_LENGTH, rc, (long)colDataSize); + LogMsg(DEBUG, messageStr, fileName); if ( rc != SQL_SUCCESS ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); PyErr_Clear(); Py_RETURN_FALSE; } + snprintf(messageStr, sizeof(messageStr), "Column width: %ld", (long)colDataSize); + LogMsg(INFO, messageStr, fileName); + LogMsg(INFO, "exit field_width()", fileName); return PyInt_FromLong(colDataSize); } @@ -8620,19 +10908,33 @@ static PyObject *ibm_db_field_width(PyObject *self, PyObject *args) */ static PyObject *ibm_db_cursor_type(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry cursor_type()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; stmt_handle *stmt_res = NULL; - if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) + if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p", py_stmt_res); + LogMsg(DEBUG, messageStr, fileName); if (NIL_P(py_stmt_res) || (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType))) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } - + long result = (stmt_res->cursor_type != SQL_SCROLL_FORWARD_ONLY); + snprintf(messageStr, sizeof(messageStr), "Cursor type check result: %ld", result); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit cursor_type()", fileName); return PyInt_FromLong(stmt_res->cursor_type != SQL_SCROLL_FORWARD_ONLY); } @@ -8663,21 +10965,32 @@ static PyObject *ibm_db_cursor_type(PyObject *self, PyObject *args) */ static PyObject *ibm_db_rollback(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry rollback()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; conn_handle *conn_res; int rc; - if (!PyArg_ParseTuple(args, "O", &py_conn_res)) + if (!PyArg_ParseTuple(args, "O", &py_conn_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p", py_conn_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); return NULL; } @@ -8685,16 +10998,21 @@ static PyObject *ibm_db_rollback(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; rc = SQLEndTran(SQL_HANDLE_DBC, conn_res->hdbc, SQL_ROLLBACK); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLEndTran called with parambets SQL_HANDLE_DBC=%d, conn_res->hdbc=%p, SQL_ROLLBACK=%d and returned rc=%d", + SQL_HANDLE_DBC, (void *)conn_res->hdbc, SQL_ROLLBACK, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); PyErr_Clear(); Py_RETURN_FALSE; } else { + LogMsg(INFO, "Successfully completed rollback operation", fileName); + LogMsg(INFO, "exit rollback()", fileName); Py_RETURN_TRUE; } } + LogMsg(INFO, "exit rollback()", fileName); Py_RETURN_FALSE; } @@ -8720,19 +11038,30 @@ static PyObject *ibm_db_rollback(PyObject *self, PyObject *args) */ static PyObject *ibm_db_free_stmt(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry free_stmt()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; stmt_handle *handle; SQLRETURN rc; - if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) + if (!PyArg_ParseTuple(args, "O", &py_stmt_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p", py_stmt_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_stmt_res)) { if (PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { handle = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle to be freed: handle->hstmt=%p", (void *)handle->hstmt); + LogMsg(DEBUG, messageStr, fileName); if (handle->hstmt != -1) { Py_BEGIN_ALLOW_THREADS; rc = SQLFreeHandle( SQL_HANDLE_STMT, handle->hstmt); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLFreeHandle called with SQL_HANDLE_STMT abd handle=%p and returned rc=%d", (void *)handle->hstmt, rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( handle->hstmt, @@ -8744,27 +11073,37 @@ static PyObject *ibm_db_free_stmt(PyObject *self, PyObject *args) } _python_ibm_db_free_result_struct(handle); handle->hstmt = -1; + LogMsg(INFO, "exit free_stmt()", fileName); Py_RETURN_TRUE; } } } + LogMsg(INFO, "exit free_stmt()", fileName); Py_RETURN_NONE; } /* static RETCODE _python_ibm_db_get_data(stmt_handle *stmt_res, int col_num, short ctype, void *buff, int in_length, SQLINTEGER *out_length) */ static RETCODE _python_ibm_db_get_data(stmt_handle *stmt_res, int col_num, short ctype, void *buff, int in_length, SQLINTEGER *out_length) { + LogMsg(INFO, "entry _python_ibm_db_get_data()", fileName); + snprintf(messageStr, sizeof(messageStr), "stmt_res=%p, col_num=%d, ctype=%d, buff=%p, in_length=%d, out_length=%p", + (void *)stmt_res, col_num, ctype, buff, in_length, (void *)out_length); + LogMsg(DEBUG, messageStr, fileName); RETCODE rc = SQL_SUCCESS; - + snprintf(messageStr, sizeof(messageStr), + "Calling SQLGetData: hstmt=%p, col_num=%d, ctype=%d, buff=%p, in_length=%d, out_length=%p", + (void *)stmt_res->hstmt, col_num, ctype, buff, in_length, (void *)out_length); + LogMsg(INFO, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLGetData((SQLHSTMT)stmt_res->hstmt, col_num, ctype, buff, in_length, out_length); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetData returned: rc=%d", rc); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } + LogMsg(INFO, "exit _python_ibm_db_get_data()", fileName); return rc; } @@ -8793,6 +11132,10 @@ static RETCODE _python_ibm_db_get_data(stmt_handle *stmt_res, int col_num, short */ static PyObject *ibm_db_result(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry result()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; PyObject *column = NULL; #if PY_MAJOR_VERSION >= 3 @@ -8806,7 +11149,7 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) DATE_STRUCT *date_ptr; TIME_STRUCT *time_ptr; TIMESTAMP_STRUCT *ts_ptr; - char error[DB2_MAX_ERR_MSG_LEN + 50]; + char error[DB2_MAX_ERR_MSG_LEN +50]; SQLINTEGER in_length, out_length = -10; /* Initialize out_length to some * meaningless value * */ @@ -8815,28 +11158,39 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) SQLINTEGER long_val; PyObject *return_value = NULL; - if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) + if (!PyArg_ParseTuple(args, "OO", &py_stmt_res, &column)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, column=%p", py_stmt_res, column); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_stmt_res)) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(EXCEPTION, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if ( TYPE(column) == PYTHON_FIXNUM ) { col_num = PyLong_AsLong(column); + snprintf(messageStr, sizeof(messageStr), "Column number (integer): %ld", col_num); + LogMsg(DEBUG, messageStr, fileName); } else if (PyString_Check(column)) { #if PY_MAJOR_VERSION >= 3 col_name_py3_tmp = PyUnicode_AsASCIIString(column); if (col_name_py3_tmp == NULL) { + LogMsg(ERROR, "Failed to convert column name to ASCII string", fileName); return NULL; } column = col_name_py3_tmp; #endif + snprintf(messageStr, sizeof(messageStr), "Column name: %s", PyBytes_AsString(column)); + LogMsg(DEBUG, messageStr, fileName); col_num = _python_ibm_db_get_column_by_name(stmt_res, PyBytes_AsString(column), -1); #if PY_MAJOR_VERSION >= 3 if ( col_name_py3_tmp != NULL ) { @@ -8845,6 +11199,7 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) #endif } else { /* Column argument has to be either an integer or string */ + LogMsg(ERROR, "Column argument must be an integer or string", fileName); Py_RETURN_FALSE; } @@ -8854,6 +11209,7 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) sprintf(error, "Column information cannot be retrieved: %s", IBM_DB_G(__python_stmt_err_msg)); strcpy(IBM_DB_G(__python_stmt_err_msg), error); + LogMsg(ERROR, error, fileName); PyErr_Clear(); Py_RETURN_FALSE; } @@ -8861,12 +11217,15 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) if(col_num < 0 || col_num >= stmt_res->num_columns) { strcpy(IBM_DB_G(__python_stmt_err_msg), "Column ordinal out of range"); + LogMsg(ERROR, "Column ordinal out of range", fileName); PyErr_Clear(); Py_RETURN_NONE; } /* get the data */ column_type = stmt_res->column_info[col_num].type; + snprintf(messageStr, sizeof(messageStr), "Processing column type: %d", column_type); + LogMsg(DEBUG, messageStr, fileName); switch(column_type) { case SQL_CHAR: case SQL_VARCHAR: @@ -8896,14 +11255,18 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) memset(out_ptr,0,sizeof(Py_UNICODE)*in_length); if ( out_ptr == NULL ) { + LogMsg(ERROR, "Failed to allocate memory for data", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return NULL; } rc = _python_ibm_db_get_data(stmt_res, col_num+1, SQL_C_WCHAR, out_ptr, in_length * sizeof(Py_UNICODE), &out_length); + snprintf(messageStr, sizeof(messageStr), "values received rc: %d, out_length: %d", rc, out_length); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { + LogMsg(ERROR, "An error occurred while retrieving data", fileName); if(out_ptr != NULL) { PyMem_Del(out_ptr); out_ptr = NULL; @@ -8920,22 +11283,29 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) // as it treats 00 in 2 bytes for each char as NULL else { return_value = getSQLWCharAsPyUnicodeObject(out_ptr, out_length); + snprintf(messageStr, sizeof(messageStr), "Data content: %s", PyUnicode_AsUTF8(return_value)); + LogMsg(DEBUG, messageStr, fileName); } PyMem_Del(out_ptr); out_ptr = NULL; + LogMsg(DEBUG, "exit result()", fileName); return return_value; case SQL_TYPE_DATE: date_ptr = ALLOC(DATE_STRUCT); if (date_ptr == NULL) { + LogMsg(ERROR, "Failed to allocate memory for DATE_STRUCT", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return NULL; } rc = _python_ibm_db_get_data(stmt_res, col_num+1, SQL_C_TYPE_DATE, date_ptr, sizeof(DATE_STRUCT), &out_length); + snprintf(messageStr, sizeof(messageStr), "SQL_Get_Data for DATE returned rc: %d, out_length: %d", rc, out_length); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { + LogMsg(ERROR, "An error occurred while retrieving DATE data", fileName); if(date_ptr != NULL) { PyMem_Del(date_ptr); date_ptr = NULL; @@ -8949,8 +11319,11 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) Py_RETURN_NONE; } else { return_value = PyDate_FromDate(date_ptr->year, date_ptr->month, date_ptr->day); + snprintf(messageStr, sizeof(messageStr), "Retrieved DATE value: %ld-%02ld-%02ld", date_ptr->year, date_ptr->month, date_ptr->day); + LogMsg(DEBUG, messageStr, fileName); PyMem_Del(date_ptr); date_ptr = NULL; + LogMsg(DEBUG, "exit result()", fileName); return return_value; } break; @@ -8958,14 +11331,18 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) case SQL_TYPE_TIME: time_ptr = ALLOC(TIME_STRUCT); if (time_ptr == NULL) { + LogMsg(ERROR, "Failed to allocate memory for TIME_STRUCT", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return NULL; } rc = _python_ibm_db_get_data(stmt_res, col_num+1, SQL_C_TYPE_TIME, time_ptr, sizeof(TIME_STRUCT), &out_length); + snprintf(messageStr, sizeof(messageStr), "SQL_Get_Data for TIME returned rc: %d, out_length: %d", rc, out_length); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { + LogMsg(ERROR, "An error occurred while retrieving TIME data", fileName); if(time_ptr != NULL) { PyMem_Del(time_ptr); time_ptr = NULL; @@ -8980,8 +11357,11 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) Py_RETURN_NONE; } else { return_value = PyTime_FromTime(time_ptr->hour % 24, time_ptr->minute, time_ptr->second, 0); + snprintf(messageStr, sizeof(messageStr), "Retrieved TIME value: %02d:%02d:%02d", time_ptr->hour, time_ptr->minute, time_ptr->second); + LogMsg(DEBUG, messageStr, fileName); PyMem_Del(time_ptr); time_ptr = NULL; + LogMsg(INFO, "exit result()", fileName); return return_value; } break; @@ -8989,14 +11369,18 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) case SQL_TYPE_TIMESTAMP: ts_ptr = ALLOC(TIMESTAMP_STRUCT); if (ts_ptr == NULL) { + LogMsg(ERROR, "Failed to allocate memory for TIMESTAMP_STRUCT", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return NULL; } rc = _python_ibm_db_get_data(stmt_res, col_num+1, SQL_C_TYPE_TIMESTAMP, ts_ptr, sizeof(TIMESTAMP_STRUCT), &out_length); + snprintf(messageStr, sizeof(messageStr), "SQL_Get_Data for TIMESTAMP returned rc: %d, out_length: %d", rc, out_length); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { + LogMsg(ERROR, "An error occurred while retrieving TIMESTAMP data", fileName); if(ts_ptr != NULL) { PyMem_Del(ts_ptr); time_ptr = NULL; @@ -9011,8 +11395,12 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) Py_RETURN_NONE; } else { return_value = PyDateTime_FromDateAndTime(ts_ptr->year, ts_ptr->month, ts_ptr->day, ts_ptr->hour % 24, ts_ptr->minute, ts_ptr->second, ts_ptr->fraction / 1000); + snprintf(messageStr, sizeof(messageStr), "Retrieved TIMESTAMP value: %ld-%02ld-%02ld %02d:%02d:%02d.%03d", + ts_ptr->year, ts_ptr->month, ts_ptr->day, ts_ptr->hour, ts_ptr->minute, ts_ptr->second, ts_ptr->fraction / 1000); + LogMsg(DEBUG, messageStr, fileName); PyMem_Del(ts_ptr); ts_ptr = NULL; + LogMsg(DEBUG, "exit result()", fileName); return return_value; } break; @@ -9028,13 +11416,19 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) rc = _python_ibm_db_get_data(stmt_res, col_num+1, SQL_C_LONG, &long_val, sizeof(long_val), &out_length); + snprintf(messageStr, sizeof(messageStr), "SQL_Get_Data returned rc: %d, out_length: %d", rc, out_length); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { + LogMsg(ERROR, "An error occurred while retrieving BOOLEAN data", fileName); PyErr_Clear(); Py_RETURN_FALSE; } if (out_length == SQL_NULL_DATA) { Py_RETURN_NONE; } else { + snprintf(messageStr, sizeof(messageStr), "Retrieved BOOLEAN value: %ld", long_val); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit result()", fileName); return PyInt_FromLong(long_val); } break; @@ -9043,13 +11437,19 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) rc = _python_ibm_db_get_data(stmt_res, col_num+1, SQL_C_LONG, &long_val, sizeof(long_val), &out_length); + snprintf(messageStr, sizeof(messageStr), "SQL_Get_Data returned rc: %d, out_length: %d", rc, out_length); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { + LogMsg(ERROR, "An error occurred while retrieving BIT data", fileName); PyErr_Clear(); Py_RETURN_FALSE; } if (out_length == SQL_NULL_DATA) { Py_RETURN_NONE; } else { + snprintf(messageStr, sizeof(messageStr), "Retrieved BIT value: %ld", long_val); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit result()", fileName); return PyBool_FromLong(long_val); } break; @@ -9061,13 +11461,19 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) rc = _python_ibm_db_get_data(stmt_res, col_num+1, SQL_C_DOUBLE, &double_val, sizeof(double_val), &out_length); + snprintf(messageStr, sizeof(messageStr), "SQL_Get_Data returned rc: %d, out_length: %d", rc, out_length); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { + LogMsg(ERROR, "An error occurred while retrieving REAL/FLOAT/DOUBLE data", fileName); PyErr_Clear(); Py_RETURN_FALSE; } if (out_length == SQL_NULL_DATA) { Py_RETURN_NONE; } else { + snprintf(messageStr, sizeof(messageStr), "Retrieved REAL/FLOAT/DOUBLE value: %f", double_val); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit result()", fileName); return PyFloat_FromDouble(double_val); } break; @@ -9080,18 +11486,23 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) case SQL_VARBINARY: switch (stmt_res->s_bin_mode) { case PASSTHRU: + LogMsg(DEBUG, "SQL_BLOB/SQL_BINARY/SQL_LONGVARBINARY/SQL_VARBINARY - PASSTHRU mode, returning empty bytes", fileName); + LogMsg(INFO, "exit result()", fileName); return PyBytes_FromStringAndSize("", 0); break; /* returns here */ case CONVERT: targetCType = SQL_C_CHAR; len_terChar = sizeof(char); + LogMsg(DEBUG, "SQL_BLOB/SQL_BINARY/SQL_LONGVARBINARY/SQL_VARBINARY - CONVERT mode, using SQL_C_CHAR", fileName); break; case BINARY: targetCType = SQL_C_BINARY; len_terChar = 0; + LogMsg(DEBUG, "SQL_BLOB/SQL_BINARY/SQL_LONGVARBINARY/SQL_VARBINARY - BINARY mode, using SQL_C_BINARY", fileName); break; default: + LogMsg(INFO, "exit result()", fileName); Py_RETURN_FALSE; } case SQL_XML: @@ -9100,15 +11511,19 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) if (column_type == SQL_CLOB || column_type == SQL_DBCLOB || column_type == SQL_XML) { len_terChar = sizeof(SQLWCHAR); targetCType = SQL_C_WCHAR; + LogMsg(DEBUG, "Setting len_terChar to sizeof(SQLWCHAR) and targetCType to SQL_C_WCHAR", fileName); } out_ptr = ALLOC_N(char, INIT_BUFSIZ + len_terChar); if ( out_ptr == NULL ) { + LogMsg(ERROR, "Failed to allocate memory for XML data", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory for XML Data"); return NULL; } rc = _python_ibm_db_get_data(stmt_res, col_num + 1, targetCType, out_ptr, INIT_BUFSIZ + len_terChar, &out_length); + snprintf(messageStr, sizeof(messageStr), "SQL_Get_Data returned rc: %d, out_length: %d", rc, out_length); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_SUCCESS_WITH_INFO ) { void *tmp_out_ptr = NULL; @@ -9119,7 +11534,11 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) rc = _python_ibm_db_get_data(stmt_res, col_num + 1, targetCType, (char *)out_ptr + INIT_BUFSIZ, out_length + len_terChar, &out_length); + snprintf(messageStr, sizeof(messageStr), "SQL_Get_Data continued with rc: %d, out_length: %d", rc, out_length); + LogMsg(DEBUG, messageStr, fileName); + if (rc == SQL_ERROR) { + LogMsg(ERROR, "An error occurred while retrieving XML/CLOB/DBCLOB data", fileName); PyMem_Del(out_ptr); out_ptr = NULL; return NULL; @@ -9132,6 +11551,7 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) } else if ( rc == SQL_ERROR ) { PyMem_Del(out_ptr); out_ptr = NULL; + LogMsg(INFO, "exit result()", fileName); Py_RETURN_FALSE; } else { if (out_length == SQL_NULL_DATA) { @@ -9139,8 +11559,10 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) retVal = Py_None; } else { if (len_terChar == 0) { + LogMsg(INFO, "Processing SQLWCHAR data", fileName); retVal = PyBytes_FromStringAndSize((char *)out_ptr, out_length); } else { + LogMsg(INFO, "Processing byte data", fileName); retVal = getSQLWCharAsPyUnicodeObject(out_ptr, out_length); } } @@ -9150,13 +11572,17 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) PyMem_Del(out_ptr); out_ptr = NULL; } + LogMsg(INFO, "exit result()", fileName); return retVal; default: break; } } else { + LogMsg(ERROR, "Supplied parameter is invalid", fileName); + LogMsg(INFO, "exit result()", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); } + LogMsg(INFO, "exit result()", fileName); Py_RETURN_FALSE; } @@ -9165,6 +11591,7 @@ static PyObject *ibm_db_result(PyObject *self, PyObject *args) */ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) { + LogMsg(INFO, "entry _python_ibm_db_bind_fetch_helper()", fileName); int rc = -1; int column_number; SQLINTEGER row_number = -1; @@ -9183,21 +11610,30 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) PyObject *py_row_number = NULL; char error[DB2_MAX_ERR_MSG_LEN +50]; - if (!PyArg_ParseTuple(args, "O|O", &py_stmt_res, &py_row_number)) + if (!PyArg_ParseTuple(args, "O|O", &py_stmt_res, &py_row_number)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, py_row_number=%p", py_stmt_res, py_row_number); + LogMsg(DEBUG, messageStr, fileName); if (NIL_P(py_stmt_res) || (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType))) { PyErr_SetString(PyExc_Exception, "Supplied statement object parameter is invalid"); + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle set. Address of stmt_res: %p", (void*)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if (!NIL_P(py_row_number)) { if (PyInt_Check(py_row_number)) { - row_number = (SQLINTEGER) PyInt_AsLong(py_row_number); + row_number = (SQLINTEGER) PyLong_AsLong(py_row_number); + snprintf(messageStr, sizeof(messageStr), "row_number: %d", row_number); + LogMsg(DEBUG, messageStr, fileName); } else { PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); + LogMsg(EXCEPTION, "Supplied parameter is invalid", fileName); return NULL; } } @@ -9209,6 +11645,7 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) sprintf(error, "Column information cannot be retrieved: %s", IBM_DB_G(__python_stmt_err_msg)); PyErr_SetString(PyExc_Exception, error); + LogMsg(ERROR, error, fileName); return NULL; } } @@ -9219,6 +11656,7 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) sprintf(error, "Column binding cannot be done: %s", IBM_DB_G(__python_stmt_err_msg)); PyErr_SetString(PyExc_Exception, error); + LogMsg(ERROR, error, fileName); return NULL; } } @@ -9227,9 +11665,15 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) #ifndef PASE /* i5/OS problem with SQL_FETCH_ABSOLUTE (temporary until fixed) */ if (is_systemi) { + LogMsg(DEBUG, "Calling SQLFetchScroll with SQL_FETCH_FIRST", fileName); + snprintf(messageStr, sizeof(messageStr), "Statement Handle: %p, row_number: %d",(void *)stmt_res->hstmt, + row_number); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFetchScroll((SQLHSTMT)stmt_res->hstmt, SQL_FETCH_FIRST, row_number); + snprintf(messageStr, sizeof(messageStr), "SQLFetchScroll returned with rc: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, SQL_HANDLE_STMT, @@ -9238,10 +11682,16 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) } Py_END_ALLOW_THREADS; - if (row_number>1 && (rc == SQL_SUCCESS || rc == SQL_SUCCESS_WITH_INFO)) + if (row_number>1 && (rc == SQL_SUCCESS || rc == SQL_SUCCESS_WITH_INFO)) { + LogMsg(DEBUG, "Calling SQLFetchScroll with SQL_FETCH_RELATIVE", fileName); + snprintf(messageStr, sizeof(messageStr), "Statement Handle: %p, row_number: %d",(void *)stmt_res->hstmt, + row_number-1); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFetchScroll((SQLHSTMT)stmt_res->hstmt, SQL_FETCH_RELATIVE, row_number-1); + snprintf(messageStr, sizeof(messageStr), "SQLFetchScroll returned with rc: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, SQL_HANDLE_STMT, @@ -9249,10 +11699,17 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) NULL, -1 ,1); } Py_END_ALLOW_THREADS; + } } else { + LogMsg(DEBUG, "Calling SQLFetchScroll with SQL_FETCH_ABSOLUTE", fileName); + snprintf(messageStr, sizeof(messageStr), "Statement Handle: %p, row_number: %d",(void *)stmt_res->hstmt, + row_number); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFetchScroll((SQLHSTMT)stmt_res->hstmt, SQL_FETCH_ABSOLUTE, row_number); + snprintf(messageStr, sizeof(messageStr), "SQLFetchScroll returned with rc: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, SQL_HANDLE_STMT, @@ -9262,9 +11719,15 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) Py_END_ALLOW_THREADS; } #else /* PASE */ + LogMsg(DEBUG, "Calling SQLFetchScroll with SQL_FETCH_FIRST", fileName); + snprintf(messageStr, sizeof(messageStr), "Statement Handle: %p, row_number: %d",(void *)stmt_res->hstmt, + row_number); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFetchScroll((SQLHSTMT)stmt_res->hstmt, SQL_FETCH_FIRST, row_number); + snprintf(messageStr, sizeof(messageStr), "SQLFetchScroll returned with rc: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, SQL_HANDLE_STMT, @@ -9273,11 +11736,17 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) } Py_END_ALLOW_THREADS; - if (row_number>1 && (rc == SQL_SUCCESS || rc == SQL_SUCCESS_WITH_INFO)) + if (row_number>1 && (rc == SQL_SUCCESS || rc == SQL_SUCCESS_WITH_INFO)) { + LogMsg(DEBUG, "Calling SQLFetchScroll with SQL_FETCH_RELATIVE", fileName); + snprintf(messageStr, sizeof(messageStr), "Statement Handle: %p, row_number: %d",(void *)stmt_res->hstmt, + row_number-1); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFetchScroll((SQLHSTMT)stmt_res->hstmt, SQL_FETCH_RELATIVE, row_number-1); + snprintf(messageStr, sizeof(messageStr), "SQLFetchScroll returned with rc: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, SQL_HANDLE_STMT, @@ -9285,16 +11754,22 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) NULL, -1, 1); } Py_END_ALLOW_THREADS; + } #endif /* PASE */ } else if (PyTuple_Size(args) == 2 && row_number < 0) { PyErr_SetString(PyExc_Exception, "Requested row number must be a positive value"); + LogMsg(EXCEPTION, "Requested row number must be a positive value", fileName); return NULL; } else { /* row_number is NULL or 0; just fetch next row */ + LogMsg(DEBUG, "Calling SQLFetch, for fetching next row", fileName); + snprintf(messageStr, sizeof(messageStr), "Statement Handle: %p",(void *)stmt_res->hstmt); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFetch((SQLHSTMT)stmt_res->hstmt); + snprintf(messageStr, sizeof(messageStr), "SQLFetch returned with rc: %d", rc); if( rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, @@ -9306,11 +11781,22 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) if (rc == SQL_NO_DATA_FOUND) { Py_INCREF(Py_False); + LogMsg(INFO, "exit _python_ibm_db_bind_fetch_helper()", fileName); + if( op == FETCH_ASSOC) { + LogMsg(INFO, "exit fetch_assoc()", fileName); + } + if( op == FETCH_INDEX) { + LogMsg(INFO, "exit fetch_tuple()", fileName); + } + if ( op == FETCH_BOTH) { + LogMsg(INFO, "exit fetch_both()", fileName); + } return Py_False; } else if ( rc != SQL_SUCCESS && rc != SQL_SUCCESS_WITH_INFO) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); sprintf(error, "Fetch Failure: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } @@ -9321,8 +11807,11 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) } /* copy the data over return_value */ if ( op & FETCH_ASSOC ) { + LogMsg(INFO, "Creating dict for FETCH_ASSOC", fileName); return_value = PyDict_New(); } else if ( op == FETCH_INDEX ) { + snprintf(messageStr, sizeof(messageStr), "Creating tuple for FETCH_INDEX with size %d", stmt_res->num_columns); + LogMsg(INFO, messageStr, fileName); return_value = PyTuple_New(stmt_res->num_columns); } @@ -9331,22 +11820,28 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) row_data = &stmt_res->row_data[column_number].data; out_length = stmt_res->row_data[column_number].out_length; + snprintf(messageStr, sizeof(messageStr), "Processing column %d: type=%d, out_length=%d", column_number, column_type, out_length); + LogMsg(DEBUG, messageStr, fileName); switch(stmt_res->s_case_mode) { case CASE_LOWER: + LogMsg(INFO, "Column name changing to lower case", fileName); stmt_res->column_info[column_number].name = (SQLCHAR*)strtolower((char*)stmt_res->column_info[column_number].name, strlen((char*)stmt_res->column_info[column_number].name)); break; case CASE_UPPER: + LogMsg(INFO, "Column name changing to upper case", fileName); stmt_res->column_info[column_number].name = (SQLCHAR*)strtoupper((char*)stmt_res->column_info[column_number].name, strlen((char*)stmt_res->column_info[column_number].name)); break; case CASE_NATURAL: default: + LogMsg(INFO, "Column name unchanged", fileName); break; } if (out_length == SQL_NULL_DATA) { + LogMsg(DEBUG, "Column data is SQL_NULL_DATA", fileName); Py_INCREF(Py_None); value = Py_None; } else { @@ -9356,6 +11851,8 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) if ( stmt_res->s_use_wchar == WCHAR_NO ) { tmp_length = stmt_res->column_info[column_number].size; value = PyBytes_FromStringAndSize((char *)row_data->str_val, out_length); + snprintf(messageStr, sizeof(messageStr), "Column data converted to bytes, with value: %p", (void *)value); + LogMsg(DEBUG, messageStr, fileName); break; } case SQL_WCHAR: @@ -9365,6 +11862,8 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) case SQL_LONGVARGRAPHIC: tmp_length = stmt_res->column_info[column_number].size; value = getSQLWCharAsPyUnicodeObject(row_data->w_val, out_length); + snprintf(messageStr, sizeof(messageStr), "Column data converted to unicode, with value: %p", (void *)value); + LogMsg(DEBUG, messageStr, fileName); break; #ifndef PASE /* i5/OS SQL_LONGVARCHAR is SQL_VARCHAR */ @@ -9374,16 +11873,21 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) #endif /* PASE */ /* i5/OS will xlate from EBCIDIC to ASCII (via SQLGetData) */ tmp_length = stmt_res->column_info[column_number].size; - + snprintf(messageStr, sizeof(messageStr), "Allocating memory for column %d with size %d", column_number, tmp_length + 1); + LogMsg(DEBUG, messageStr, fileName); wout_ptr = (SQLWCHAR *)ALLOC_N(SQLWCHAR, tmp_length + 1); if ( wout_ptr == NULL ) { PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); + LogMsg(EXCEPTION, "Failed to Allocate Memory", fileName); return NULL; } /* _python_ibm_db_get_data null terminates all output. */ + LogMsg(DEBUG, "Fetching data for column", fileName); rc = _python_ibm_db_get_data(stmt_res, column_number + 1, SQL_C_WCHAR, wout_ptr, (tmp_length * sizeof(SQLWCHAR) + 1), &out_length); + snprintf(messageStr, sizeof(messageStr), "Fetch result for column %d: rc=%d, out_length=%d", column_number, rc, out_length); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { return NULL; } @@ -9392,6 +11896,7 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) value = Py_None; } else { value = getSQLWCharAsPyUnicodeObject(wout_ptr, out_length); + LogMsg(DEBUG, "Column data converted to unicode after fetch", fileName); } if (wout_ptr != NULL) { PyMem_Del(wout_ptr); @@ -9402,25 +11907,35 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) case SQL_DECIMAL: case SQL_NUMERIC: case SQL_DECFLOAT: - value = StringOBJ_FromASCIIAndSize((char *)row_data->str_val, out_length); + value = StringOBJ_FromASCIIAndSize((char *)row_data->str_val, out_length); + LogMsg(DEBUG, "Column data converted to decimal", fileName); break; case SQL_TYPE_DATE: value = PyDate_FromDate(row_data->date_val->year, row_data->date_val->month, row_data->date_val->day); + LogMsg(DEBUG, "Column data converted to date", fileName); break; case SQL_TYPE_TIME: value = PyTime_FromTime(row_data->time_val->hour % 24, row_data->time_val->minute, row_data->time_val->second, 0); + LogMsg(DEBUG, "Column data converted to time", fileName); break; case SQL_TYPE_TIMESTAMP: value = PyDateTime_FromDateAndTime(row_data->ts_val->year, row_data->ts_val->month, row_data->ts_val->day, row_data->ts_val->hour % 24, row_data->ts_val->minute, row_data->ts_val->second, row_data->ts_val->fraction / 1000); + snprintf(messageStr, sizeof(messageStr), + "Column data converted to timestamp: year=%d, month=%d, day=%d, hour=%d, minute=%d, second=%d, fraction=%d", + row_data->ts_val->year, row_data->ts_val->month, row_data->ts_val->day, + row_data->ts_val->hour % 24, row_data->ts_val->minute, row_data->ts_val->second, + row_data->ts_val->fraction / 1000); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_BIGINT: value = PyLong_FromString((char *)row_data->str_val, NULL, 10); + LogMsg(DEBUG, "Column data converted to string", fileName); break; #ifdef __MVS__ @@ -9430,26 +11945,38 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) case SQL_BOOLEAN: #endif value = PyInt_FromLong(row_data->s_val); + snprintf(messageStr, sizeof(messageStr), "SQL_SMALLINT/SQL_BOOLEAN: value=%ld", row_data->s_val); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_INTEGER: value = PyInt_FromLong(row_data->i_val); + snprintf(messageStr, sizeof(messageStr), "SQL_INTEGER: value=%ld", row_data->i_val); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_BIT: value = PyBool_FromLong(row_data->i_val); + snprintf(messageStr, sizeof(messageStr), "SQL_BIT: value=%s", row_data->i_val ? "True" : "False"); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_REAL: value = PyFloat_FromDouble(row_data->r_val); + snprintf(messageStr, sizeof(messageStr), "SQL_REAL: value=%f", row_data->r_val); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_FLOAT: value = PyFloat_FromDouble(row_data->f_val); + snprintf(messageStr, sizeof(messageStr), "SQL_FLOAT: value=%f", row_data->f_val); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_DOUBLE: value = PyFloat_FromDouble(row_data->d_val); + snprintf(messageStr, sizeof(messageStr), "SQL_DOUBLE: value=%f", row_data->d_val); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_BINARY: @@ -9462,23 +11989,34 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) } else { value = PyBytes_FromStringAndSize((char *)row_data->str_val, out_length); } + snprintf(messageStr, sizeof(messageStr), "SQL_BINARY/SQL_VARBINARY: value size=%d", out_length); + LogMsg(DEBUG, messageStr, fileName); break; case SQL_BLOB: + snprintf(messageStr, sizeof(messageStr), "SQL_BLOB: Binary Mode = %d", stmt_res->s_bin_mode); + LogMsg(DEBUG, messageStr, fileName); switch (stmt_res->s_bin_mode) { case PASSTHRU: + LogMsg(DEBUG, "SQL_BLOB: PASSTHRU mode selected", fileName); Py_RETURN_NONE; break; case CONVERT: len_terChar = sizeof(char); targetCType = SQL_C_CHAR; + snprintf(messageStr, sizeof(messageStr), "SQL_BLOB: CONVERT mode selected. len_terChar = %d, targetCType = %d", len_terChar, targetCType); + LogMsg(DEBUG, messageStr, fileName); break; case BINARY: len_terChar = 0; targetCType = SQL_C_BINARY; + snprintf(messageStr, sizeof(messageStr), "SQL_BLOB: BINARY mode selected. len_terChar = %d, targetCType = %d", len_terChar, targetCType); + LogMsg(DEBUG, messageStr, fileName); break; default: len_terChar = -1; + snprintf(messageStr, sizeof(messageStr), "SQL_BLOB: Default mode selected. len_terChar = %d", len_terChar); + LogMsg(DEBUG, messageStr, fileName); break; } case SQL_XML: @@ -9487,20 +12025,28 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) if (column_type == SQL_CLOB || column_type == SQL_DBCLOB || column_type == SQL_XML) { len_terChar = sizeof(SQLWCHAR); targetCType = SQL_C_WCHAR; + snprintf(messageStr, sizeof(messageStr), "SQL_DBCLOB: Conversion settings. len_terChar = %d, targetCType = %d", len_terChar, targetCType); + LogMsg(DEBUG, messageStr, fileName); } else if (len_terChar == -1) { break; } out_ptr = (void *)ALLOC_N(char, INIT_BUFSIZ + len_terChar); if (out_ptr == NULL) { + snprintf(messageStr, sizeof(messageStr), "SQL_DBCLOB: Failed to Allocate Memory for LOB Data. INIT_BUFSIZ = %d, len_terChar = %d", INIT_BUFSIZ, len_terChar); + LogMsg(ERROR, messageStr, fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory for LOB Data"); return NULL; } rc = _python_ibm_db_get_data(stmt_res, column_number + 1, targetCType, out_ptr, INIT_BUFSIZ + len_terChar, &out_length); + snprintf(messageStr, sizeof(messageStr), "Fetching data: rc = %d, INIT_BUFSIZ = %d, len_terChar = %d, out_length = %d", rc, INIT_BUFSIZ, len_terChar, out_length); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_SUCCESS_WITH_INFO) { void *tmp_out_ptr = NULL; + snprintf(messageStr, sizeof(messageStr), "SQL_SUCCESS_WITH_INFO received. Preparing to allocate more memory. Initial out_length = %d", out_length); + LogMsg(DEBUG, messageStr, fileName); tmp_out_ptr = (void *)ALLOC_N(char, out_length + INIT_BUFSIZ + len_terChar); memcpy(tmp_out_ptr, out_ptr, INIT_BUFSIZ); PyMem_Del(out_ptr); @@ -9508,6 +12054,8 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) rc = _python_ibm_db_get_data(stmt_res, column_number + 1, targetCType, (char *)out_ptr + INIT_BUFSIZ, out_length + len_terChar, &out_length); + snprintf(messageStr, sizeof(messageStr), "Second fetch attempt: rc = %d, out_length = %d", rc, out_length); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { if (out_ptr != NULL) { PyMem_Del(out_ptr); @@ -9516,12 +12064,17 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) sprintf(error, "Failed to fetch LOB Data: %s", IBM_DB_G(__python_stmt_err_msg)); PyErr_SetString(PyExc_Exception, error); + LogMsg(ERROR, error, fileName); return NULL; } if (len_terChar == sizeof(SQLWCHAR)) { + snprintf(messageStr, sizeof(messageStr), "Processing SQLWCHAR data: len_terChar = %d", len_terChar); + LogMsg(DEBUG, messageStr, fileName); value = getSQLWCharAsPyUnicodeObject(out_ptr, INIT_BUFSIZ + out_length); } else { + snprintf(messageStr, sizeof(messageStr), "Processing binary data: len_terChar = %d", len_terChar); + LogMsg(DEBUG, messageStr, fileName); value = PyBytes_FromStringAndSize((char*)out_ptr, INIT_BUFSIZ + out_length); } } else if ( rc == SQL_ERROR ) { @@ -9530,6 +12083,7 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) sprintf(error, "Failed to LOB Data: %s", IBM_DB_G(__python_stmt_err_msg)); PyErr_SetString(PyExc_Exception, error); + LogMsg(ERROR, error, fileName); return NULL; } else { if (out_length == SQL_NULL_DATA) { @@ -9537,8 +12091,12 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) value = Py_None; } else { if (len_terChar == sizeof(SQLWCHAR)) { + snprintf(messageStr, sizeof(messageStr), "Processing SQLWCHAR data: len_terChar = %d", len_terChar); + LogMsg(DEBUG, messageStr, fileName); value = getSQLWCharAsPyUnicodeObject(out_ptr, out_length); } else { + snprintf(messageStr, sizeof(messageStr), "Processing binary data: len_terChar = %d", len_terChar); + LogMsg(DEBUG, messageStr, fileName); value = PyBytes_FromStringAndSize((char*)out_ptr, out_length); } } @@ -9564,17 +12122,25 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) if (value == NULL) { Py_XDECREF(key); Py_XDECREF(value); + snprintf(messageStr, sizeof(messageStr), "Error: Value is NULL for FETCH_ASSOC operation. Column: %s", stmt_res->column_info[column_number].name); + LogMsg(ERROR, messageStr, fileName); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Fetching column %d as key-value pair", column_number); + LogMsg(DEBUG, messageStr, fileName); PyDict_SetItem(return_value, key, value); Py_DECREF(key); } if (op == FETCH_INDEX) { /* No need to call Py_DECREF as PyTuple_SetItem steals the reference */ + snprintf(messageStr, sizeof(messageStr), "Fetching column %d as index for FETCH_INDEX", column_number); + LogMsg(DEBUG, messageStr, fileName); PyTuple_SetItem(return_value, column_number, value); } else { if (op == FETCH_BOTH) { key = PyInt_FromLong(column_number); + snprintf(messageStr, sizeof(messageStr), "Fetching column %d as key-value pair", column_number); + LogMsg(DEBUG, messageStr, fileName); PyDict_SetItem(return_value, key, value); Py_DECREF(key); } @@ -9583,10 +12149,21 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) } if( rc == SQL_SUCCESS_WITH_INFO ) { + snprintf(messageStr, sizeof(messageStr), "SQL_SUCCESS_WITH_INFO: Checking SQL errors for statement handle %p", stmt_res->hstmt); + LogMsg(INFO, messageStr, fileName); _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1,NULL, -1, 1); } - + LogMsg(INFO, "exit _python_ibm_db_bind_fetch_helper()", fileName); + if( op == FETCH_ASSOC) { + LogMsg(INFO, "exit fetch_assoc()", fileName); + } + if( op == FETCH_INDEX) { + LogMsg(INFO, "exit fetch_tuple()", fileName); + } + if ( op == FETCH_BOTH) { + LogMsg(INFO, "exit fetch_both()", fileName); + } return return_value; } @@ -9621,28 +12198,39 @@ static PyObject *_python_ibm_db_bind_fetch_helper(PyObject *args, int op) */ static PyObject *ibm_db_fetch_row(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry fetch_row()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_stmt_res = NULL; PyObject *py_row_number = NULL; SQLINTEGER row_number = -1; stmt_handle* stmt_res = NULL; int rc; - char error[DB2_MAX_ERR_MSG_LEN + 50]; + char error[DB2_MAX_ERR_MSG_LEN +50]; - if (!PyArg_ParseTuple(args, "O|O", &py_stmt_res, &py_row_number)) + if (!PyArg_ParseTuple(args, "O|O", &py_stmt_res, &py_row_number)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, py_row_number=%p", py_stmt_res, py_row_number); + LogMsg(DEBUG, messageStr, fileName); if (NIL_P(py_stmt_res) || (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType))) { PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if (!NIL_P(py_row_number)) { if (PyInt_Check(py_row_number)) { - row_number = (SQLINTEGER) PyInt_AsLong(py_row_number); + row_number = (SQLINTEGER) PyLong_AsLong(py_row_number); } else { PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); + LogMsg(ERROR, "Supplied parameter is invalid", fileName); return NULL; } } @@ -9652,6 +12240,7 @@ static PyObject *ibm_db_fetch_row(PyObject *self, PyObject *args) sprintf(error, "Column information cannot be retrieved: %s", IBM_DB_G(__python_stmt_err_msg)); PyErr_SetString(PyExc_Exception, error); + LogMsg(ERROR, error, fileName); return NULL; } } @@ -9660,9 +12249,15 @@ static PyObject *ibm_db_fetch_row(PyObject *self, PyObject *args) if (PyTuple_Size(args) == 2 && row_number > 0) { #ifndef PASE /* i5/OS problem with SQL_FETCH_ABSOLUTE */ + LogMsg(DEBUG, "Calling SQLFetchScroll with SQL_FETCH_ABSOLUTE", fileName); + snprintf(messageStr, sizeof(messageStr), "Statement Handle: %p, row_number: %d",(void *)stmt_res->hstmt, + row_number); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFetchScroll((SQLHSTMT)stmt_res->hstmt, SQL_FETCH_ABSOLUTE, row_number); + snprintf(messageStr, sizeof(messageStr), "SQLFetchScroll returned with rc: %d", rc); + LogMsg(DEBUG, messageStr, fileName); Py_END_ALLOW_THREADS; if( rc == SQL_SUCCESS_WITH_INFO ) { @@ -9671,9 +12266,15 @@ static PyObject *ibm_db_fetch_row(PyObject *self, PyObject *args) -1,1); } #else /* PASE */ + LogMsg(DEBUG, "Calling SQLFetchScroll with SQL_FETCH_FIRST", fileName); + snprintf(messageStr, sizeof(messageStr), "Statement Handle: %p, row_number: %d",(void *)stmt_res->hstmt, + row_number); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFetchScroll((SQLHSTMT)stmt_res->hstmt, SQL_FETCH_FIRST, row_number); + snprintf(messageStr, sizeof(messageStr), "SQLFetchScroll returned with rc: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, @@ -9682,10 +12283,16 @@ static PyObject *ibm_db_fetch_row(PyObject *self, PyObject *args) } Py_END_ALLOW_THREADS; - if (row_number>1 && (rc == SQL_SUCCESS || rc == SQL_SUCCESS_WITH_INFO)) + if (row_number>1 && (rc == SQL_SUCCESS || rc == SQL_SUCCESS_WITH_INFO)) { + LogMsg(DEBUG, "Calling SQLFetchScroll with SQL_FETCH_RELATIVE", fileName); + snprintf(messageStr, sizeof(messageStr), "Statement Handle: %p, row_number: %d",(void *)stmt_res->hstmt, + row_number-1); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFetchScroll((SQLHSTMT)stmt_res->hstmt, SQL_FETCH_RELATIVE, row_number-1); + snprintf(messageStr, sizeof(messageStr), "SQLFetchScroll returned with rc: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if( rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, @@ -9693,15 +12300,22 @@ static PyObject *ibm_db_fetch_row(PyObject *self, PyObject *args) -1,1); } Py_END_ALLOW_THREADS; + } #endif /* PASE */ } else if (PyTuple_Size(args) == 2 && row_number < 0) { PyErr_SetString(PyExc_Exception, "Requested row number must be a positive value"); + LogMsg(ERROR, "Requested row number must be a positive value", fileName); return NULL; } else { /* row_number is NULL or 0; just fetch next row */ + LogMsg(DEBUG, "Calling SQLFetch, for fetching next row", fileName); + snprintf(messageStr, sizeof(messageStr), "Statement Handle: %p",(void *)stmt_res->hstmt); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLFetch((SQLHSTMT)stmt_res->hstmt); + snprintf(messageStr, sizeof(messageStr), "SQLFetch returned with rc: %d", rc); + LogMsg(DEBUG, messageStr, fileName); Py_END_ALLOW_THREADS; } @@ -9712,13 +12326,16 @@ static PyObject *ibm_db_fetch_row(PyObject *self, PyObject *args) SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } + LogMsg(INFO, "exit fetch_row()", fileName); Py_RETURN_TRUE; } else if (rc == SQL_NO_DATA_FOUND) { + LogMsg(INFO, "exit fetch_row()", fileName); Py_RETURN_FALSE; } else { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); PyErr_Clear(); + LogMsg(INFO, "exit fetch_row()", fileName); Py_RETURN_FALSE; } } @@ -9750,6 +12367,7 @@ static PyObject *ibm_db_fetch_row(PyObject *self, PyObject *args) */ static PyObject *ibm_db_fetch_assoc(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry fetch_assoc()", fileName); return _python_ibm_db_bind_fetch_helper(args, FETCH_ASSOC); } @@ -9832,6 +12450,7 @@ PyObject *ibm_db_fetch_object(int argc, PyObject **argv, PyObject *self) */ static PyObject *ibm_db_fetch_array(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry fetch_tuple()", fileName); return _python_ibm_db_bind_fetch_helper(args, FETCH_INDEX); } @@ -9862,6 +12481,7 @@ static PyObject *ibm_db_fetch_array(PyObject *self, PyObject *args) */ static PyObject *ibm_db_fetch_both(PyObject *self, PyObject *args) { + LogMsg(INFO,"entry fetch_both()", fileName); return _python_ibm_db_bind_fetch_helper(args, FETCH_BOTH); } @@ -9891,6 +12511,10 @@ static PyObject *ibm_db_fetch_both(PyObject *self, PyObject *args) */ static PyObject *ibm_db_set_option(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry set_option()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *conn_or_stmt = NULL; PyObject *options = NULL; PyObject *py_type = NULL; @@ -9899,29 +12523,44 @@ static PyObject *ibm_db_set_option(PyObject *self, PyObject *args) int rc = 0; long type = 0; - if (!PyArg_ParseTuple(args, "OOO", &conn_or_stmt, &options, &py_type)) + if (!PyArg_ParseTuple(args, "OOO", &conn_or_stmt, &options, &py_type)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: conn_or_stmt=%p, options=%p, py_type=%p", + (void *)conn_or_stmt, (void *)options, (void *)py_type); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(conn_or_stmt)) { if (!NIL_P(py_type)) { if (PyInt_Check(py_type)) { - type = (int) PyInt_AsLong(py_type); + type = (int) PyLong_AsLong(py_type); + snprintf(messageStr, sizeof(messageStr), "type: %ld", type); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Supplied py_type parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } } if ( type == 1 ) { if (!PyObject_TypeCheck(conn_or_stmt, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } conn_res = (conn_handle *)conn_or_stmt; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); if ( !NIL_P(options) ) { - rc = _python_ibm_db_parse_options(options, SQL_HANDLE_DBC, - conn_res); + snprintf(messageStr, sizeof(messageStr), "Calling _python_ibm_db_parse_options with: (options=%p, SQL_HANDLE_DBC=%d, conn_res=%p)", + (void *)options, SQL_HANDLE_DBC, (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); + rc = _python_ibm_db_parse_options(options, SQL_HANDLE_DBC, conn_res); + snprintf(messageStr, sizeof(messageStr), "_python_ibm_db_parse_options returned rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { + LogMsg(ERROR, "Options array must have string indexes", fileName); PyErr_SetString(PyExc_Exception, "Options Array must have string indexes"); return NULL; @@ -9929,24 +12568,34 @@ static PyObject *ibm_db_set_option(PyObject *self, PyObject *args) } } else { if (!PyObject_TypeCheck(conn_or_stmt, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } stmt_res = (stmt_handle *)conn_or_stmt; - + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); if ( !NIL_P(options) ) { - rc = _python_ibm_db_parse_options(options, SQL_HANDLE_STMT, - stmt_res); + snprintf(messageStr, sizeof(messageStr), "Calling _python_ibm_db_parse_options with: (options=%p, SQL_HANDLE_STMT=%d, stmt_res=%p)", (void *)options, SQL_HANDLE_STMT, (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); + rc = _python_ibm_db_parse_options(options, SQL_HANDLE_STMT, stmt_res); + snprintf(messageStr, sizeof(messageStr), "_python_ibm_db_parse_options returned rc=%d", rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { + LogMsg(ERROR, "Options array must have string indexes", fileName); PyErr_SetString(PyExc_Exception, "Options Array must have string indexes"); return NULL; } } } + LogMsg(DEBUG, "successfully set option", fileName); + LogMsg(INFO, "exit set_option()", fileName); Py_INCREF(Py_True); return Py_True; } else { + LogMsg(DEBUG, "failed to set option", fileName); + LogMsg(INFO, "exit set_option()", fileName); Py_INCREF(Py_False); return Py_False; } @@ -9954,6 +12603,10 @@ static PyObject *ibm_db_set_option(PyObject *self, PyObject *args) static PyObject *ibm_db_get_db_info(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry get_db_info()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; PyObject *return_value = NULL; PyObject *py_option = NULL; @@ -9962,36 +12615,51 @@ static PyObject *ibm_db_get_db_info(PyObject *self, PyObject *args) int rc = 0; SQLCHAR *value=NULL; - if (!PyArg_ParseTuple(args, "OO", &py_conn_res, &py_option)) + if (!PyArg_ParseTuple(args, "OO", &py_conn_res, &py_option)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, py_option=%p", py_conn_res, py_option); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res=%p", conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!NIL_P(py_option)) { if (PyInt_Check(py_option)) { - option = (SQLINTEGER) PyInt_AsLong(py_option); + option = (SQLINTEGER) PyLong_AsLong(py_option); + snprintf(messageStr, sizeof(messageStr), "Option parsed: option=%d", option); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Supplied parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); return NULL; } value = (SQLCHAR*)ALLOC_N(char, ACCTSTR_LEN + 1); - + snprintf(messageStr, sizeof(messageStr), + "Calling SQLGetInfo with parameters: hdbc=%p, option=%d, buffer=%p, buffer_length=%d", + conn_res->hdbc, option, value, ACCTSTR_LEN); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLGetInfo(conn_res->hdbc, (SQLSMALLINT)option, (SQLPOINTER)value, ACCTSTR_LEN, NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLGetInfo returned rc=%d, value=%s", rc, value ? (char *)value : "NULL"); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10013,9 +12681,11 @@ static PyObject *ibm_db_get_db_info(PyObject *self, PyObject *args) PyMem_Del(value); value = NULL; } + LogMsg(INFO, "exit get_db_info()", fileName); return return_value; } } + LogMsg(INFO, "exit get_db_info()", fileName); Py_INCREF(Py_False); return Py_False; } @@ -10136,6 +12806,10 @@ static PyObject *ibm_db_get_db_info(PyObject *self, PyObject *args) */ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry server_info()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; conn_handle *conn_res; int rc = 0; @@ -10156,18 +12830,25 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) le_server_info *return_value = PyObject_NEW(le_server_info, &server_infoType); - if (!PyArg_ParseTuple(args, "O", &py_conn_res)) + if (!PyArg_ParseTuple(args, "O", &py_conn_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p", py_conn_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); return NULL; } @@ -10179,13 +12860,18 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_DBMS_NAME, (SQLPOINTER)buffer255, sizeof(buffer255), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_DBMS_NAME=%d, buffer255=%p, buffer255_size=%zu, NULL, and returned rc=%d, buffer255 contains: %s", + conn_res->hdbc, SQL_DBMS_NAME, (void *)buffer255, sizeof(buffer255), rc, buffer255); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); PyErr_Clear(); Py_RETURN_FALSE; } else { + snprintf(messageStr, sizeof(messageStr), "Setting return_value->DBMS_NAME to: %s", buffer255); + LogMsg(DEBUG, messageStr, fileName); return_value->DBMS_NAME = StringOBJ_FromASCII(buffer255); } @@ -10196,7 +12882,10 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_DBMS_VER, (SQLPOINTER)buffer11, sizeof(buffer11), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_DBMS_VER=%d, buffer11=%p, buffer11_size=%zu, NULL and returned rc=%d, buffer11 contains: %s", + conn_res->hdbc, SQL_DBMS_VER, (void *)buffer11, sizeof(buffer11), rc, buffer11); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10209,10 +12898,14 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } - return_value->DBMS_VER = StringOBJ_FromASCII(buffer11); + snprintf(messageStr, sizeof(messageStr), "Setting return_value->DBMS_VER to: %s", buffer11); + LogMsg(DEBUG, messageStr, fileName); + return_value->DBMS_VER = StringOBJ_FromASCII(buffer11); } #if defined(__MVS__) + snprintf(messageStr, sizeof(messageStr), "Setting return_value->DB_CODEPAGE to: %ld", 1208); + LogMsg(DEBUG, messageStr, fileName); return_value->DB_CODEPAGE = PyInt_FromLong(1208); #elif !defined(PASE) /* i5/OS DB_CODEPAGE handled natively */ /* DB_CODEPAGE */ @@ -10222,7 +12915,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_DATABASE_CODEPAGE, &bufferint32, sizeof(bufferint32), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_DATABASE_CODEPAGE=%d, bufferint32=%p, bufferint32_size=%zu, NULL and returned rc=%d, bufferint32 contains: %d", + conn_res->hdbc, SQL_DATABASE_CODEPAGE, (void *)&bufferint32, sizeof(bufferint32), rc, bufferint32); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10235,6 +12930,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->DB_CODEPAGE to: %ld", bufferint32); + LogMsg(DEBUG, messageStr, fileName); return_value->DB_CODEPAGE = PyInt_FromLong(bufferint32); } #endif /* PASE */ @@ -10246,7 +12943,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_DATABASE_NAME, (SQLPOINTER)buffer255, sizeof(buffer255), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_DATABASE_NAME=%d, buffer255=%p, buffer255_size=%zu, NULL and returned rc=%d, buffer255 contains: %s", + conn_res->hdbc, SQL_DATABASE_NAME, (void *)buffer255, sizeof(buffer255), rc, buffer255); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10259,6 +12958,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->DB_NAME to: %s", buffer255); + LogMsg(DEBUG, messageStr, fileName); return_value->DB_NAME = StringOBJ_FromASCII(buffer255); } @@ -10270,7 +12971,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_SERVER_NAME, (SQLPOINTER)buffer255, sizeof(buffer255), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_SERVER_NAME=%d, buffer255=%p, buffer255_size=%zu, NULL and returned rc=%d, buffer255 contains: %s", + conn_res->hdbc, SQL_SERVER_NAME, (void *)buffer255, sizeof(buffer255), rc, buffer255); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10283,6 +12986,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->INST_NAME to: %s", buffer255); + LogMsg(DEBUG, messageStr, fileName); return_value->INST_NAME = StringOBJ_FromASCII(buffer255); } @@ -10293,7 +12998,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_SPECIAL_CHARACTERS, (SQLPOINTER)buffer255, sizeof(buffer255), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_SPECIAL_CHARACTERS=%d, buffer255=%p, buffer255_size=%zu, NULL and returned rc=%d, buffer255 contains: %s", + conn_res->hdbc, SQL_SPECIAL_CHARACTERS, (void *)buffer255, sizeof(buffer255), rc, buffer255); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10306,6 +13013,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->SPECIAL_CHARS to: %s", buffer255); + LogMsg(DEBUG, messageStr, fileName); return_value->SPECIAL_CHARS = StringOBJ_FromASCII(buffer255); } #endif /* PASE */ @@ -10317,7 +13026,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_KEYWORDS, (SQLPOINTER)buffer2k, sizeof(buffer2k), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_KEYWORDS=%d, buffer2k=%p, buffer2k_size=%zu, NULL and returned rc=%d, buffer2k contains: %s", + conn_res->hdbc, SQL_KEYWORDS, (void *)buffer2k, sizeof(buffer2k), rc, buffer2k); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10336,6 +13047,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) numkw++; } } + snprintf(messageStr, sizeof(messageStr), "Parsed KEYWORDS buffer. Total keywords count is: %d", numkw); + LogMsg(DEBUG, messageStr, fileName); karray = PyTuple_New(numkw+1); for (keyword = last = buffer2k; *last; last++) { @@ -10346,8 +13059,11 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) count++; } } - if (*keyword) + if (*keyword) { PyTuple_SetItem(karray, count, StringOBJ_FromASCII(keyword)); + } + snprintf(messageStr, sizeof(messageStr), "Set return_value->KEYWORDS to a tuple with %d items.", numkw); + LogMsg(DEBUG, messageStr, fileName); return_value->KEYWORDS = karray; } @@ -10359,7 +13075,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_DEFAULT_TXN_ISOLATION, &bitmask, sizeof(bitmask), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_DEFAULT_TXN_ISOLATION=%d, &bitmask=%p, bitmask_size=%zu, NULL and returned rc=%d, bitmask=0x%x", + conn_res->hdbc, SQL_DEFAULT_TXN_ISOLATION, (void *)&bitmask, sizeof(bitmask), rc, bitmask); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10374,19 +13092,26 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) } if( bitmask & SQL_TXN_READ_UNCOMMITTED ) { strcpy((char *)buffer11, "UR"); + LogMsg(DEBUG, "bitmask indicates SQL_TXN_READ_UNCOMMITTED. Setting buffer11 to: UR", fileName); } if( bitmask & SQL_TXN_READ_COMMITTED ) { strcpy((char *)buffer11, "CS"); + LogMsg(DEBUG, "bitmask indicates SQL_TXN_READ_COMMITTED. Setting buffer11 to: CS", fileName); } if( bitmask & SQL_TXN_REPEATABLE_READ ) { strcpy((char *)buffer11, "RS"); + LogMsg(DEBUG, "bitmask indicates SQL_TXN_REPEATABLE_READ. Setting buffer11 to: RS", fileName); } if( bitmask & SQL_TXN_SERIALIZABLE ) { strcpy((char *)buffer11, "RR"); + LogMsg(DEBUG, "bitmask indicates SQL_TXN_SERIALIZABLE. Setting buffer11 to: RR", fileName); } if( bitmask & SQL_TXN_NOCOMMIT ) { strcpy((char *)buffer11, "NC"); + LogMsg(DEBUG, "bitmask indicates SQL_TXN_NOCOMMIT. Setting buffer11 to: NC", fileName); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->DFT_ISOLATION to: %s", buffer11); + LogMsg(DEBUG, messageStr, fileName); return_value->DFT_ISOLATION = StringOBJ_FromASCII(buffer11); } @@ -10400,7 +13125,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_TXN_ISOLATION_OPTION, &bitmask, sizeof(bitmask), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_TXN_ISOLATION_OPTION=%d, &bitmask=%p, bitmask_size=%zu, NULL and returned rc=%d, bitmask=0x%x", + conn_res->hdbc, SQL_TXN_ISOLATION_OPTION, (void *)&bitmask, sizeof(bitmask), rc, bitmask); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10418,26 +13145,32 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) if( bitmask & SQL_TXN_READ_UNCOMMITTED ) { PyTuple_SetItem(array, count, StringOBJ_FromASCII("UR")); + LogMsg(DEBUG, "Bitmask indicates SQL_TXN_READ_UNCOMMITTED. Added 'UR' to the tuple.", fileName); count++; } if( bitmask & SQL_TXN_READ_COMMITTED ) { PyTuple_SetItem(array, count, StringOBJ_FromASCII("CS")); + LogMsg(DEBUG, "Bitmask indicates SQL_TXN_READ_COMMITTED. Added 'CS' to the tuple.", fileName); count++; } if( bitmask & SQL_TXN_REPEATABLE_READ ) { PyTuple_SetItem(array, count, StringOBJ_FromASCII("RS")); + LogMsg(DEBUG, "Bitmask indicates SQL_TXN_REPEATABLE_READ. Added 'RS' to the tuple.", fileName); count++; } if( bitmask & SQL_TXN_SERIALIZABLE ) { PyTuple_SetItem(array, count, StringOBJ_FromASCII("RR")); + LogMsg(DEBUG, "Bitmask indicates SQL_TXN_SERIALIZABLE. Added 'RR' to the tuple.", fileName); count++; } if( bitmask & SQL_TXN_NOCOMMIT ) { PyTuple_SetItem(array, count, StringOBJ_FromASCII("NC")); + LogMsg(DEBUG, "Bitmask indicates SQL_TXN_NOCOMMIT. Added 'NC' to the tuple.", fileName); count++; } _PyTuple_Resize(&array, count); - + snprintf(messageStr, sizeof(messageStr), "Setting return_value->ISOLATION_OPTION to a tuple with %d items.", count); + LogMsg(DEBUG, messageStr, fileName); return_value->ISOLATION_OPTION = array; } #endif /* PASE */ @@ -10450,7 +13183,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_ODBC_SQL_CONFORMANCE, &bufferint32, sizeof(bufferint32), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_ODBC_SQL_CONFORMANCE=%d, &bufferint32=%p, bufferint32_size=%zu, NULL and returned rc=%d, bufferint32=%d", + conn_res->hdbc, SQL_ODBC_SQL_CONFORMANCE, (void *)&bufferint32, sizeof(bufferint32), rc, bufferint32); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10466,19 +13201,25 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) switch (bufferint32) { case SQL_SC_SQL92_ENTRY: strcpy((char *)buffer255, "ENTRY"); + LogMsg(DEBUG, "Bitmask indicates SQL_SC_SQL92_ENTRY. Setting buffer255 to 'ENTRY'.", fileName); break; case SQL_SC_FIPS127_2_TRANSITIONAL: strcpy((char *)buffer255, "FIPS127"); + LogMsg(DEBUG, "Bitmask indicates SQL_SC_FIPS127_2_TRANSITIONAL. Setting buffer255 to 'FIPS127'.", fileName); break; case SQL_SC_SQL92_FULL: strcpy((char *)buffer255, "FULL"); + LogMsg(DEBUG, "Bitmask indicates SQL_SC_SQL92_FULL. Setting buffer255 to 'FULL'.", fileName); break; case SQL_SC_SQL92_INTERMEDIATE: strcpy((char *)buffer255, "INTERMEDIATE"); + LogMsg(DEBUG, "Bitmask indicates SQL_SC_SQL92_INTERMEDIATE. Setting buffer255 to 'INTERMEDIATE'.", fileName); break; default: break; } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->SQL_CONFORMANCE to: %s", buffer255); + LogMsg(DEBUG, messageStr, fileName); return_value->SQL_CONFORMANCE = StringOBJ_FromASCII(buffer255); } @@ -10489,7 +13230,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_PROCEDURES, (SQLPOINTER)buffer11, sizeof(buffer11), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_PROCEDURES=%d, (SQLPOINTER)buffer11=%p, buffer11_size=%zu, NULL and returned rc=%d, buffer11 contains: %s", + conn_res->hdbc, SQL_PROCEDURES, (void *)buffer11, sizeof(buffer11), rc, buffer11); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10503,9 +13246,11 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) NULL, -1, 1); } if( strcmp((char *)buffer11, "Y") == 0 ) { + LogMsg(DEBUG, "SQL_PROCEDURES value is 'Y'. Setting return_value->PROCEDURES to Py_True.", fileName); Py_INCREF(Py_True); return_value->PROCEDURES = Py_True; } else { + LogMsg(DEBUG, "SQL_PROCEDURES value is not 'Y'. Setting return_value->PROCEDURES to Py_False.", fileName); Py_INCREF(Py_False); return_value->PROCEDURES = Py_False; } @@ -10518,7 +13263,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_IDENTIFIER_QUOTE_CHAR, (SQLPOINTER)buffer11, sizeof(buffer11), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_IDENTIFIER_QUOTE_CHAR=%d, (SQLPOINTER)buffer11=%p, buffer11_size=%zu, NULL and returned rc=%d, buffer11 contains: %s", + conn_res->hdbc, SQL_IDENTIFIER_QUOTE_CHAR, (void *)buffer11, sizeof(buffer11), rc, buffer11); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10531,6 +13278,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->IDENTIFIER_QUOTE_CHAR to: %s", buffer11); + LogMsg(DEBUG, messageStr, fileName); return_value->IDENTIFIER_QUOTE_CHAR = StringOBJ_FromASCII(buffer11); } @@ -10541,7 +13290,10 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_LIKE_ESCAPE_CLAUSE, (SQLPOINTER)buffer11, sizeof(buffer11), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_LIKE_ESCAPE_CLAUSE=%d, (SQLPOINTER)buffer11=%p, buffer11_size=%zu, NULL and returned rc=%d, buffer11 contains: %s", + conn_res->hdbc, SQL_LIKE_ESCAPE_CLAUSE, (void *)buffer11, sizeof(buffer11), rc, buffer11); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10555,9 +13307,11 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) NULL, -1, 1); } if( strcmp(buffer11, "Y") == 0 ) { + LogMsg(DEBUG, "SQL_LIKE_ESCAPE_CLAUSE value is 'Y'. Setting return_value->LIKE_ESCAPE_CLAUSE to Py_True.", fileName); Py_INCREF(Py_True); return_value->LIKE_ESCAPE_CLAUSE = Py_True; } else { + LogMsg(DEBUG, "SQL_LIKE_ESCAPE_CLAUSE value is not 'Y'. Setting return_value->LIKE_ESCAPE_CLAUSE to Py_False.", fileName); Py_INCREF(Py_False); return_value->LIKE_ESCAPE_CLAUSE = Py_False; } @@ -10570,7 +13324,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_MAX_COLUMN_NAME_LEN, &bufferint16, sizeof(bufferint16), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_MAX_COLUMN_NAME_LEN=%d, &bufferint16=%p, bufferint16_size=%zu, NULL and returned rc=%d, bufferint16 contains: %d", + conn_res->hdbc, SQL_MAX_COLUMN_NAME_LEN, (void *)&bufferint16, sizeof(bufferint16), rc, bufferint16); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10583,6 +13339,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->MAX_COL_NAME_LEN to: %d", bufferint16); + LogMsg(DEBUG, messageStr, fileName); return_value->MAX_COL_NAME_LEN = PyInt_FromLong(bufferint16); } @@ -10593,7 +13351,10 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_MAX_ROW_SIZE, &bufferint32, sizeof(bufferint32), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), + "SQLGetInfo called with conn_res->hdbc=%p, SQL_MAX_ROW_SIZE=%d, &bufferint32=%p, bufferint32_size=%zu, NULL and returned rc=%d, bufferint32 contains: %d", + conn_res->hdbc, SQL_MAX_ROW_SIZE, (void *)&bufferint32, sizeof(bufferint32), rc, bufferint32); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10606,6 +13367,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->MAX_ROW_SIZE to: %d", bufferint32); + LogMsg(DEBUG, messageStr, fileName); return_value->MAX_ROW_SIZE = PyInt_FromLong(bufferint32); } @@ -10617,7 +13380,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_MAX_IDENTIFIER_LEN, &bufferint16, sizeof(bufferint16), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_MAX_IDENTIFIER_LEN=%d, &bufferint16=%p, bufferint16_size=%zu, NULL and returned rc=%d, bufferint16 contains: %d", + conn_res->hdbc, SQL_MAX_IDENTIFIER_LEN, (void *)&bufferint16, sizeof(bufferint16), rc, bufferint16); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10630,6 +13395,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->MAX_IDENTIFIER_LEN to: %d", bufferint16); + LogMsg(DEBUG, messageStr, fileName); return_value->MAX_IDENTIFIER_LEN = PyInt_FromLong(bufferint16); } @@ -10640,7 +13407,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_MAX_INDEX_SIZE, &bufferint32, sizeof(bufferint32), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_MAX_INDEX_SIZE=%d, &bufferint32=%p, bufferint32_size=%zu, NULL and returned rc=%d, bufferint32 contains: %d", + conn_res->hdbc, SQL_MAX_INDEX_SIZE, (void *)&bufferint32, sizeof(bufferint32), rc, bufferint32); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10653,6 +13422,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->MAX_INDEX_SIZE to: %d", bufferint32); + LogMsg(DEBUG, messageStr, fileName); return_value->MAX_INDEX_SIZE = PyInt_FromLong(bufferint32); } @@ -10663,7 +13434,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_MAX_PROCEDURE_NAME_LEN, &bufferint16, sizeof(bufferint16), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_MAX_PROCEDURE_NAME_LEN=%d, &bufferint16=%p, bufferint16_size=%zu, NULL and returned rc=%d, bufferint16 contains: %d", + conn_res->hdbc, SQL_MAX_PROCEDURE_NAME_LEN, (void *)&bufferint16, sizeof(bufferint16), rc, bufferint16); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10676,6 +13449,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->MAX_PROC_NAME_LEN to: %d", bufferint16); + LogMsg(DEBUG, messageStr, fileName); return_value->MAX_PROC_NAME_LEN = PyInt_FromLong(bufferint16); } #endif /* PASE */ @@ -10687,7 +13462,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_MAX_SCHEMA_NAME_LEN, &bufferint16, sizeof(bufferint16), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_MAX_SCHEMA_NAME_LEN=%d, &bufferint16=%p, bufferint16_size=%zu, NULL and returned rc=%d, bufferint16 contains: %d", + conn_res->hdbc, SQL_MAX_SCHEMA_NAME_LEN, (void *)&bufferint16, sizeof(bufferint16), rc, bufferint16); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10700,6 +13477,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->MAX_SCHEMA_NAME_LEN to: %d", bufferint16); + LogMsg(DEBUG, messageStr, fileName); return_value->MAX_SCHEMA_NAME_LEN = PyInt_FromLong(bufferint16); } @@ -10710,7 +13489,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_MAX_STATEMENT_LEN, &bufferint32, sizeof(bufferint32), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_MAX_STATEMENT_LEN=%d, &bufferint32=%p, bufferint32_size=%zu, NULL and returned rc=%d, bufferint32 contains: %d", + conn_res->hdbc, SQL_MAX_STATEMENT_LEN, (void *)&bufferint32, sizeof(bufferint32), rc, bufferint32); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10723,6 +13504,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->MAX_STATEMENT_LEN to: %d", bufferint32); + LogMsg(DEBUG, messageStr, fileName); return_value->MAX_STATEMENT_LEN = PyInt_FromLong(bufferint32); } @@ -10733,7 +13516,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_MAX_TABLE_NAME_LEN, &bufferint16, sizeof(bufferint16), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_MAX_TABLE_NAME_LEN=%d, &bufferint16=%p, bufferint16_size=%zu, NULL and returned rc=%d, bufferint16 contains: %d", + conn_res->hdbc, SQL_MAX_TABLE_NAME_LEN, (void *)&bufferint16, sizeof(bufferint16), rc, bufferint16); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10746,6 +13531,8 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); } + snprintf(messageStr, sizeof(messageStr), "Setting return_value->MAX_TABLE_NAME_LEN to: %d", bufferint16); + LogMsg(DEBUG, messageStr, fileName); return_value->MAX_TABLE_NAME_LEN = PyInt_FromLong(bufferint16); } @@ -10757,7 +13544,9 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) rc = SQLGetInfo(conn_res->hdbc, SQL_NON_NULLABLE_COLUMNS, &bufferint16, sizeof(bufferint16), NULL); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo called with parameters conn_res->hdbc=%p, SQL_NON_NULLABLE_COLUMNS=%d, &bufferint16=%p, bufferint16_size=%zu, NULL and returned rc=%d, bufferint16 contains: %d", + conn_res->hdbc, SQL_NON_NULLABLE_COLUMNS, (void *)&bufferint16, sizeof(bufferint16), rc, bufferint16); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10772,20 +13561,27 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) } switch (bufferint16) { case SQL_NNC_NON_NULL: + LogMsg(DEBUG, "SQL_NON_NULLABLE_COLUMNS indicates non-nullable columns. Setting return_value->NON_NULLABLE_COLUMNS to Py_True.", fileName); Py_INCREF(Py_True); rv = Py_True; break; case SQL_NNC_NULL: + LogMsg(DEBUG, "SQL_NON_NULLABLE_COLUMNS indicates nullable columns. Setting return_value->NON_NULLABLE_COLUMNS to Py_False.", fileName); Py_INCREF(Py_False); rv = Py_False; break; default: + LogMsg(DEBUG, "SQL_NON_NULLABLE_COLUMNS returned an unexpected value. No action taken.", fileName); break; } return_value->NON_NULLABLE_COLUMNS = rv; } + snprintf(messageStr, sizeof(messageStr), "Returning Python object at address: %p", (void *)return_value); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit server_info()", fileName); return (PyObject *)return_value; } + LogMsg(INFO, "exit server_info()", fileName); Py_RETURN_FALSE; } @@ -10839,6 +13635,10 @@ static PyObject *ibm_db_server_info(PyObject *self, PyObject *args) */ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry client_info()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; conn_handle *conn_res = NULL; int rc = 0; @@ -10849,17 +13649,26 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) le_client_info *return_value = PyObject_NEW(le_client_info, &client_infoType); - if (!PyArg_ParseTuple(args, "O", &py_conn_res)) + if (!PyArg_ParseTuple(args, "O", &py_conn_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p", py_conn_res); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); return NULL; } @@ -10872,6 +13681,9 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) sizeof(buffer255), NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo(SQL_DRIVER_NAME) rc=%d, buffer255=%s", rc, buffer255); + LogMsg(DEBUG, messageStr, fileName); + if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10894,6 +13706,9 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) sizeof(buffer255), NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo(SQL_DRIVER_VER) rc=%d, buffer255=%s", rc, buffer255); + LogMsg(DEBUG, messageStr, fileName); + if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10917,6 +13732,9 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) (SQLPOINTER)buffer255, sizeof(buffer255), NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo(SQL_DATA_SOURCE_NAME) rc=%d, buffer255=%s", rc, buffer255); + LogMsg(DEBUG, messageStr, fileName); + if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10940,6 +13758,9 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) (SQLPOINTER)buffer255, sizeof(buffer255), NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo(SQL_DRIVER_ODBC_VER) rc=%d, buffer255=%s", rc, buffer255); + LogMsg(DEBUG, messageStr, fileName); + if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10964,6 +13785,9 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) sizeof(buffer255), NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo(SQL_ODBC_VER) rc=%d, buffer255=%s", rc, buffer255); + LogMsg(DEBUG, messageStr, fileName); + if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -10989,6 +13813,9 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) sizeof(bufferint16), NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo(SQL_ODBC_SQL_CONFORMANCE) rc=%d, bufferint16=%d", rc, bufferint16); + LogMsg(DEBUG, messageStr, fileName); + if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -11020,6 +13847,7 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) #if defined(__MVS__) return_value->APPL_CODEPAGE = PyInt_FromLong(1208); return_value->CONN_CODEPAGE = PyInt_FromLong(1208); + LogMsg(INFO, "For MVS: APPL_CODEPAGE=1208, CONN_CODEPAGE=1208", fileName); #elif !defined(PASE) /* i5/OS APPL_CODEPAGE handled natively */ /* APPL_CODEPAGE */ bufferint32 = 0; @@ -11029,6 +13857,9 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) sizeof(bufferint32), NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo(SQL_APPLICATION_CODEPAGE) rc=%d, bufferint32=%d", rc, bufferint32); + LogMsg(DEBUG, messageStr, fileName); + if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -11051,6 +13882,9 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) sizeof(bufferint32), NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetInfo(SQL_CONNECT_CODEPAGE) rc=%d, bufferint32=%d", rc, bufferint32); + LogMsg(DEBUG, messageStr, fileName); + if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -11067,8 +13901,10 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) } #endif /* PASE */ + LogMsg(INFO, "exit client_info()", fileName); return (PyObject *)return_value; } + LogMsg(INFO, "exit client_info()", fileName); PyErr_Clear(); Py_RETURN_FALSE; } @@ -11093,6 +13929,10 @@ static PyObject *ibm_db_client_info(PyObject *self, PyObject *args) */ static PyObject *ibm_db_active(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry active()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; int rc; conn_handle *conn_res = NULL; @@ -11100,22 +13940,34 @@ static PyObject *ibm_db_active(PyObject *self, PyObject *args) conn_alive = 0; - if (!PyArg_ParseTuple(args, "O", &py_conn_res)) + if (!PyArg_ParseTuple(args, "O", &py_conn_res)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p", py_conn_res); + LogMsg(DEBUG, messageStr, fileName); if (!(NIL_P(py_conn_res) || (py_conn_res == Py_None))) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } #if !defined(PASE) && !defined(__MVS__) Py_BEGIN_ALLOW_THREADS; rc = SQLGetConnectAttr(conn_res->hdbc, SQL_ATTR_PING_DB, (SQLPOINTER)&conn_alive, 0, NULL); + snprintf(messageStr, sizeof(messageStr), + "SQLGetConnectAttr executed: rc=%d, conn_alive=%d", rc, conn_alive); + LogMsg(DEBUG, messageStr, fileName); Py_END_ALLOW_THREADS; if ( rc == SQL_ERROR ) { + snprintf(messageStr, sizeof(messageStr), + "SQL_ERROR occurred: rc=%d, conn_alive=%d", rc, conn_alive); + LogMsg(ERROR, messageStr, fileName); _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); PyErr_Clear(); @@ -11127,8 +13979,10 @@ static PyObject *ibm_db_active(PyObject *self, PyObject *args) * return the ping time on success. We only want success or failure. */ if (conn_alive == 0) { + LogMsg(INFO, "exit active()", fileName); Py_RETURN_FALSE; } else { + LogMsg(INFO, "exit active()", fileName); Py_RETURN_TRUE; } } @@ -11159,6 +14013,10 @@ static PyObject *ibm_db_active(PyObject *self, PyObject *args) */ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry get_option()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *conn_or_stmt = NULL; PyObject *retVal = NULL; PyObject *py_op_integer = NULL; @@ -11172,22 +14030,32 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) long type = 0; int rc; - if (!PyArg_ParseTuple(args, "OOO", &conn_or_stmt, &py_op_integer, &py_type)) + if (!PyArg_ParseTuple(args, "OOO", &conn_or_stmt, &py_op_integer, &py_type)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: conn_or_stmt=%p, py_op_integer=%p, py_type=%p", + (void *)conn_or_stmt, (void *)py_op_integer, (void *)py_type); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(conn_or_stmt)) { if (!NIL_P(py_op_integer)) { if (PyInt_Check(py_op_integer)) { - op_integer = (SQLINTEGER) PyInt_AsLong(py_op_integer); + op_integer = (SQLINTEGER) PyLong_AsLong(py_op_integer); + snprintf(messageStr, sizeof(messageStr), "op_integer: %d", op_integer); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Supplied py_op_integer parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } } if (!NIL_P(py_type)) { if (PyInt_Check(py_type)) { - type = PyInt_AsLong(py_type); + type = PyLong_AsLong(py_type); + snprintf(messageStr, sizeof(messageStr), "type: %ld", type); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Supplied py_type parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } @@ -11197,13 +14065,17 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) */ if (type == 1) { if (!PyObject_TypeCheck(conn_or_stmt, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object Parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } conn_res = (conn_handle *)conn_or_stmt; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); /* Check to ensure the connection resource given is active */ if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); return NULL; } @@ -11218,9 +14090,13 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) case SQL_ATTR_USE_TRUSTED_CONTEXT: case SQL_ATTR_TXN_ISOLATION: isInteger = 1; + snprintf(messageStr, sizeof(messageStr), "Option %d is considered integer", op_integer); + LogMsg(DEBUG, messageStr, fileName); break; default: isInteger = 0; + snprintf(messageStr, sizeof(messageStr), "Option %d is not considered integer", op_integer); + LogMsg(DEBUG, messageStr, fileName); break; } @@ -11228,6 +14104,7 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) { value = (SQLCHAR*)ALLOC_N(char, ACCTSTR_LEN + 1); if ( value == NULL ) { + LogMsg(ERROR, "Failed to Allocate Memory for value", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return NULL; } @@ -11237,6 +14114,9 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) rc = SQLGetConnectAttr((SQLHDBC)conn_res->hdbc, op_integer, (SQLPOINTER)value, ACCTSTR_LEN, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetConnectAttr called with parameters SQLHDBC=%p, op_integer=%d, value=%p, ACCTSTR_LEN=%d, and returned rc=%d", + (SQLHDBC)conn_res->hdbc, op_integer, (void *)value, ACCTSTR_LEN, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); @@ -11252,6 +14132,9 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) PyMem_Del(value); value = NULL; } + snprintf(messageStr, sizeof(messageStr), "Returning string option value: %s", PyUnicode_AsUTF8(retVal)); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit get_option()", fileName); return retVal; } else { @@ -11259,22 +14142,30 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) rc = SQLGetConnectAttr((SQLHDBC)conn_res->hdbc, op_integer, &value_int, SQL_IS_INTEGER, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetConnectAttr called with parameters SQLHDBC=%p, op_integer=%d, value_int=%p, SQL_IS_INTEGER=%d, and returned rc=%d", + (SQLHDBC)conn_res->hdbc, op_integer, (void *)&value_int, SQL_IS_INTEGER, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(conn_res->hdbc, SQL_HANDLE_DBC, rc, 1, NULL, -1, 1); PyErr_Clear(); Py_RETURN_FALSE; } + snprintf(messageStr, sizeof(messageStr), "Returning integer option value: %ld", value_int); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit get_option()", fileName); return PyInt_FromLong(value_int); } } else { + LogMsg(ERROR, "Supplied py_op_integer parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } /* At this point we know we are to retreive a statement option */ } else { stmt_res = (stmt_handle *)conn_or_stmt; - + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); /* Check that the option given is not null */ if (!NIL_P(py_op_integer)) { /* Checking that the option to get is the cursor type because that @@ -11286,9 +14177,13 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) case SQL_ATTR_ROWCOUNT_PREFETCH: case SQL_ATTR_QUERY_TIMEOUT: isInteger = 1; + snprintf(messageStr, sizeof(messageStr), "Option %d is considered integer", op_integer); + LogMsg(DEBUG, messageStr, fileName); break; default: isInteger = 0; + snprintf(messageStr, sizeof(messageStr), "Option %d is not considered integer", op_integer); + LogMsg(DEBUG, messageStr, fileName); break; } @@ -11297,6 +14192,7 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) // string value pointer value = (SQLCHAR*)ALLOC_N(char, ACCTSTR_LEN + 1); if ( value == NULL ) { + LogMsg(ERROR, "Failed to Allocate Memory for value", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return NULL; } @@ -11305,6 +14201,9 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) rc = SQLGetStmtAttr((SQLHSTMT)stmt_res->hstmt, op_integer, (SQLPOINTER)value, ACCTSTR_LEN, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetStmtAttr called with parameters SQLHSTMT=%p, op_integer=%d, value=%p, ACCTSTR_LEN=%d, and returned rc=%d", + (SQLHSTMT)stmt_res->hstmt, op_integer, (void *)value, ACCTSTR_LEN, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); if(value != NULL) { @@ -11319,6 +14218,9 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) PyMem_Del(value); value = NULL; } + snprintf(messageStr, sizeof(messageStr), "Returning string option value: %s", PyUnicode_AsUTF8(retVal)); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit get_option()", fileName); return retVal; } else { // integer value @@ -11326,34 +14228,52 @@ static PyObject *ibm_db_get_option(PyObject *self, PyObject *args) rc = SQLGetStmtAttr((SQLHSTMT)stmt_res->hstmt, op_integer, &value_int, SQL_IS_INTEGER, NULL); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetStmtAttr called with parameters SQLHSTMT=%p, op_integer=%d, value_int=%p, SQL_IS_INTEGER=%d, and returned rc=%d", + (SQLHSTMT)stmt_res->hstmt, op_integer, (void *)&value_int, SQL_IS_INTEGER, rc); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); PyErr_Clear(); Py_RETURN_FALSE; } + snprintf(messageStr, sizeof(messageStr), "Returning integer option value: %ld", value_int); + LogMsg(DEBUG, messageStr, fileName); + LogMsg(INFO, "exit get_option()", fileName); return PyInt_FromLong(value_int); } } else { + LogMsg(ERROR, "Supplied py_op_integer parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } } } + LogMsg(INFO, "exit get_option()", fileName); PyErr_Clear(); Py_RETURN_FALSE; } static int _ibm_db_chaining_flag(stmt_handle *stmt_res, SQLINTEGER flag, error_msg_node *error_list, int client_err_cnt) { + LogMsg(INFO, "entry _ibm_db_chaining_flag()", fileName); + snprintf(messageStr, sizeof(messageStr), "stmt_res=%p, flag=%d, error_list=%p, client_err_cnt=%d", + (void *)stmt_res, flag, (void *)error_list, client_err_cnt); + LogMsg(DEBUG, messageStr, fileName); #ifdef __MVS__ /* SQL_ATTR_CHAINING_BEGIN and SQL_ATTR_CHAINING_END are not defined */ + LogMsg(DEBUG, "Returning SQL_SUCCESS as SQL_ATTR_CHAINING_BEGIN and SQL_ATTR_CHAINING_END are not defined.", fileName); return SQL_SUCCESS; #else int rc; Py_BEGIN_ALLOW_THREADS; rc = SQLSetStmtAttrW((SQLHSTMT)stmt_res->hstmt, flag, (SQLPOINTER)SQL_TRUE, SQL_IS_INTEGER); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), + "Called SQLSetStmtAttrW with parameters hstmt=%p, attr=%d, value=%p, text=%d and returned rc=%d", + (void *)stmt_res->hstmt, flag, (void *)SQL_TRUE, SQL_IS_INTEGER, rc); + LogMsg(DEBUG, messageStr, fileName); if ( flag == SQL_ATTR_CHAINING_BEGIN ) { if ( rc == SQL_ERROR ) { + LogMsg(DEBUG, "SQL_ATTR_CHAINING_BEGIN encountered an error", fileName); _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); PyErr_SetString(PyExc_Exception, IBM_DB_G(__python_stmt_err_msg)); } @@ -11368,23 +14288,33 @@ static int _ibm_db_chaining_flag(stmt_handle *stmt_res, SQLINTEGER flag, error_m if ( rc != SQL_SUCCESS ) { #ifdef __MVS__ /* MVS only seems to have SQLGetDiagRec */ + LogMsg(DEBUG, "MVS only seems to have SQLGetDiagRec: setting rc to SQL_SUCCESS", fileName); rc = SQL_SUCCESS; #else + snprintf(messageStr, sizeof(messageStr), "Calling SQLGetDiagField: handle=%p, field=%d, pointer=%p, text=%d", + (void *)stmt_res->hstmt, SQL_DIAG_NUMBER, (void *)&err_cnt, SQL_IS_POINTER); + LogMsg(DEBUG, messageStr, fileName); SQLGetDiagField(SQL_HANDLE_STMT, (SQLHSTMT)stmt_res->hstmt, 0, SQL_DIAG_NUMBER, (SQLPOINTER) &err_cnt, SQL_IS_POINTER, NULL); #endif } + snprintf(messageStr, sizeof(messageStr), "Number of errors detected: err_cnt=%d, client_err_cnt=%d", err_cnt, client_err_cnt); + LogMsg(DEBUG, messageStr, fileName); errTuple = PyTuple_New(err_cnt + client_err_cnt); /* Allocate enough space for largest possible int value. */ err_fmt = (char *)PyMem_Malloc(strlen("Error 2147483647: %s\n") * (err_cnt + client_err_cnt) + 1); err_fmt[0] = '\0'; errNo = 1; while( error_list != NULL ) { + snprintf(messageStr, sizeof(messageStr), "Adding error to tuple: Error %d: %s", errNo, error_list->err_msg); + LogMsg(DEBUG, messageStr, fileName); err_fmt_offset += sprintf(err_fmt+err_fmt_offset, "Error %d: %s\n", (int)errNo, "%s"); PyTuple_SetItem(errTuple, errNo - 1, StringOBJ_FromASCII(error_list->err_msg)); error_list = error_list->next; errNo++; } for ( errNo = client_err_cnt + 1; errNo <= (err_cnt + client_err_cnt); errNo++ ) { + snprintf(messageStr, sizeof(messageStr), "Adding SQL error to tuple: Error %d", errNo); + LogMsg(DEBUG, messageStr, fileName); err_fmt_offset += sprintf(err_fmt+err_fmt_offset, "Error %d: %s\n", (int)errNo, "%s"); _python_ibm_db_check_sql_errors((SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, SQL_ERROR, 1, NULL, -1, (errNo - client_err_cnt)); PyTuple_SetItem(errTuple, errNo - 1, StringOBJ_FromASCII(IBM_DB_G(__python_stmt_err_msg))); @@ -11396,6 +14326,7 @@ static int _ibm_db_chaining_flag(stmt_handle *stmt_res, SQLINTEGER flag, error_m PyErr_SetObject(PyExc_Exception, err_msg); } } + LogMsg(INFO, "exit _ibm_db_chaining_flag()", fileName); return rc; #endif } @@ -11426,6 +14357,10 @@ static void _build_client_err_list(error_msg_node *head_error_list, char *err_ms * return NULL if batch fully or partialy fails (All the rows executed except for which error occurs). */ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { + LogMsg(INFO, "entry execute_many()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *options = NULL; PyObject *params = NULL; PyObject *py_stmt_res = NULL; @@ -11454,19 +14389,27 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { * 2. Parameters * 3. Options (optional) */ #if defined __MVS__ + LogMsg(ERROR, "Not supported: This function is currently not supported on this platform", fileName); PyErr_SetString( PyExc_Exception, "Not supported: This function is currently not supported on this platform" ); return NULL; #endif - if ( !PyArg_ParseTuple(args, "OO|O", &py_stmt_res, ¶ms, &options) ) + if ( !PyArg_ParseTuple(args, "OO|O", &py_stmt_res, ¶ms, &options) ) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_stmt_res=%p, params=%p, options=%p", py_stmt_res, params, options); + LogMsg(DEBUG, messageStr, fileName); if ( !NIL_P(py_stmt_res) ) { if (!PyObject_TypeCheck(py_stmt_res, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_stmt_res; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res: %p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } /* Free any cursors that might have been allocated in a previous call to SQLExecute */ Py_BEGIN_ALLOW_THREADS; @@ -11478,10 +14421,13 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { stmt_res->current_node = NULL; /* Bind parameters */ + snprintf(messageStr, sizeof(messageStr), "Calling SQLNumParams with statement handle: %p", (void*)stmt_res->hstmt); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLNumParams((SQLHSTMT)stmt_res->hstmt, (SQLSMALLINT*)&numOpts); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLNumParams executed with return code: %d, numOpts: %d", rc, numOpts); + LogMsg(DEBUG, messageStr, fileName); data_type = (SQLSMALLINT*)ALLOC_N(SQLSMALLINT, numOpts); ref_data_type = (SQLSMALLINT*)ALLOC_N(SQLSMALLINT, numOpts); for ( i = 0; i < numOpts; i++) { @@ -11489,12 +14435,16 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { } if ( numOpts != 0 ) { for ( i = 0; i < numOpts; i++) { + snprintf(messageStr, sizeof(messageStr), "Calling SQLDescribeParam with statement handle: %p, parameter index: %d", (void*)stmt_res->hstmt, i + 1); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLDescribeParam((SQLHSTMT)stmt_res->hstmt, i + 1, (SQLSMALLINT*)(data_type + i), &precision, (SQLSMALLINT*)&scale, (SQLSMALLINT*)&nullable); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLDescribeParam executed with return code: %d, precision: %u, scale: %d, nullable: %d", + rc, precision, scale, nullable); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors( stmt_res->hstmt, @@ -11662,6 +14612,8 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { Py_BEGIN_ALLOW_THREADS; rc = SQLBindParameter(stmt_res->hstmt, curr->param_num, curr->param_type, valueType, curr->data_type, curr->param_size, curr->scale, &curr->ivalue, 0, (SQLLEN *)&(curr->ivalue)); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLBindParameter return code: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); } @@ -11669,6 +14621,7 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { if ( rc != SQL_SUCCESS ) { sprintf(error, "Binding Error 1: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); _build_client_err_list(head_error_list, error); err_count++; break; @@ -11681,6 +14634,8 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { /* Set statement attribute SQL_ATTR_CHAINING_BEGIN */ rc = _ibm_db_chaining_flag(stmt_res, SQL_ATTR_CHAINING_BEGIN, NULL, 0); chaining_start = 1; + snprintf(messageStr, sizeof(messageStr), "SQL_ATTR_CHAINING_BEGIN flag set. rc: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc != SQL_SUCCESS ) { return NULL; } @@ -11690,12 +14645,15 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { Py_BEGIN_ALLOW_THREADS; rc = SQLExecute((SQLHSTMT)stmt_res->hstmt); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLExecute return code: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_NEED_DATA ) { SQLPOINTER valuePtr; Py_BEGIN_ALLOW_THREADS; rc = SQLParamData((SQLHSTMT)stmt_res->hstmt, (SQLPOINTER *)&valuePtr); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLParamData return code: %d", rc); + LogMsg(DEBUG, messageStr, fileName); while ( rc == SQL_NEED_DATA ) { /* passing data value for a parameter */ if ( !NIL_P(((param_node*)valuePtr)->svalue)) { @@ -11707,9 +14665,12 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { rc = SQLPutData((SQLHSTMT)stmt_res->hstmt, (SQLPOINTER)(((param_node*)valuePtr)->uvalue), ((param_node*)valuePtr)->ivalue); Py_END_ALLOW_THREADS; } + snprintf(messageStr, sizeof(messageStr), "SQLPutData return code: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); sprintf(error, "Sending data failed: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); _build_client_err_list(head_error_list, error); err_count++; break; @@ -11717,12 +14678,15 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { Py_BEGIN_ALLOW_THREADS; rc = SQLParamData((SQLHSTMT)stmt_res->hstmt, (SQLPOINTER *)&valuePtr); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLParamData return code: %d", rc); + LogMsg(DEBUG, messageStr, fileName); } } else if (rc == SQL_ERROR) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc,1, NULL, -1, 1); sprintf(error, "SQLExecute failed: %s", IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); _build_client_err_list(head_error_list, error); err_count++; @@ -11731,12 +14695,16 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { } } } else { + LogMsg(DEBUG, "No rows in parameters. Returning 0.", fileName); + LogMsg(INFO, "exit execute_many()", fileName); return PyInt_FromLong(0); } /* Set statement attribute SQL_ATTR_CHAINING_END */ rc = _ibm_db_chaining_flag(stmt_res, SQL_ATTR_CHAINING_END, head_error_list->next, err_count); + snprintf(messageStr, sizeof(messageStr), "SQL_ATTR_CHAINING_END flag set. rc: %d", rc); + LogMsg(DEBUG, messageStr, fileName); if ( head_error_list != NULL ) { error_msg_node *tmp_err = NULL; while ( head_error_list != NULL ) { @@ -11746,9 +14714,11 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { } } if ( rc != SQL_SUCCESS || err_count != 0 ) { + LogMsg(ERROR, "Errors encountered during execution", fileName); return NULL; } } else { + LogMsg(ERROR, "Supplied parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; @@ -11757,13 +14727,16 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { Py_BEGIN_ALLOW_THREADS; rc = SQLRowCount((SQLHSTMT)stmt_res->hstmt, &row_cnt); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "SQLRowCount return code: %d, row_count: %d", rc, row_cnt); + LogMsg(DEBUG, messageStr, fileName); if ( (rc == SQL_ERROR) && (stmt_res != NULL) ) { _python_ibm_db_check_sql_errors(stmt_res->hstmt, SQL_HANDLE_STMT, rc,1, NULL, -1, 1); sprintf(error, "SQLRowCount failed: %s",IBM_DB_G(__python_stmt_err_msg)); + LogMsg(ERROR, error, fileName); PyErr_SetString(PyExc_Exception, error); return NULL; } + LogMsg(INFO, "exit execute_many()", fileName); return PyInt_FromLong(row_cnt); } @@ -11792,6 +14765,10 @@ static PyObject* ibm_db_execute_many (PyObject *self, PyObject *args) { * If procedure not found than it return NULL */ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ + LogMsg(INFO, "entry callproc()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; PyObject *parameters_tuple = NULL; PyObject *outTuple = NULL, *pyprocName = NULL, *data = NULL; @@ -11801,17 +14778,25 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ int numOfParam = 0; if (!PyArg_ParseTuple(args, "OO|O", &py_conn_res, &pyprocName, ¶meters_tuple)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, pyprocName=%p, parameters_tuple=%p", (void *)py_conn_res, (void *)pyprocName, (void *)parameters_tuple); + LogMsg(DEBUG, messageStr, fileName); + if (!NIL_P(py_conn_res) && pyprocName != Py_None) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res: %p", (void *)conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (StringObj_Size(pyprocName) == 0) { + LogMsg(ERROR, "Empty Procedure Name", fileName); PyErr_SetString(PyExc_Exception, "Empty Procedure Name"); return NULL; } @@ -11823,15 +14808,19 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ PyObject *sql = NULL; int i=0; if (!PyTuple_Check(parameters_tuple)) { + LogMsg(ERROR, "Param is not a tuple", fileName); PyErr_SetString(PyExc_Exception, "Param is not a tuple"); return NULL; } numOfParam = PyTuple_Size(parameters_tuple); + snprintf(messageStr, sizeof(messageStr), "Number of parameters: %d", numOfParam); + LogMsg(DEBUG, messageStr, fileName); subsql1 = StringOBJ_FromASCII("CALL "); subsql2 = PyUnicode_Concat(subsql1, pyprocName); Py_XDECREF(subsql1); strsubsql = (char *)PyMem_Malloc(sizeof(char)*((strlen("( )") + strlen(", ?")*numOfParam) + 2)); if (strsubsql == NULL) { + LogMsg(ERROR, "Failed to Allocate Memory", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return NULL; } @@ -11849,20 +14838,30 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ sql = PyUnicode_Concat(subsql2, subsql1); Py_XDECREF(subsql1); Py_XDECREF(subsql2); + snprintf(messageStr, sizeof(messageStr), "Constructed SQL statement: %s", PyUnicode_AsUTF8(sql)); + LogMsg(DEBUG, messageStr, fileName); stmt_res = (stmt_handle *)_python_ibm_db_prepare_helper(conn_res, sql, NULL); PyMem_Del(strsubsql); Py_XDECREF(sql); if(NIL_P(stmt_res)) { + LogMsg(ERROR, "Failed to prepare statement", fileName); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Prepared statement: stmt_res=%p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); /* Bind values from the parameters_tuple to params */ for (i = 0; i < numOfParam; i++ ) { PyObject *bind_result = NULL; data = PyTuple_GET_ITEM(parameters_tuple, i); + snprintf(messageStr, sizeof(messageStr), "Binding parameter %d: data=%p", i, (void *)data); + LogMsg(DEBUG, messageStr, fileName); bind_result = _python_ibm_db_bind_param_helper(4, stmt_res, i+1, data, SQL_PARAM_INPUT_OUTPUT, 0, 0, 0, 0); if (NIL_P(bind_result)){ + LogMsg(ERROR, "Failed to bind parameter", fileName); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Bind result for parameter %d: bind_result=%p", i, (void *)bind_result); + LogMsg(DEBUG, messageStr, fileName); } } else { PyObject *subsql1 = NULL; @@ -11875,11 +14874,16 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ sql = PyUnicode_Concat(subsql2, subsql1); Py_XDECREF(subsql1); Py_XDECREF(subsql2); + snprintf(messageStr, sizeof(messageStr), "Constructed SQL statement (no parameters): %s", PyUnicode_AsUTF8(sql)); + LogMsg(DEBUG, messageStr, fileName); stmt_res = (stmt_handle *)_python_ibm_db_prepare_helper(conn_res, sql, NULL); Py_XDECREF(sql); if(NIL_P(stmt_res)) { + LogMsg(ERROR, "Failed to prepare statement", fileName); return NULL; } + snprintf(messageStr, sizeof(messageStr), "Prepared statement (no parameters): stmt_res=%p", (void *)stmt_res); + LogMsg(DEBUG, messageStr, fileName); } if (!NIL_P(_python_ibm_db_execute_helper1(stmt_res, NULL))) { @@ -11901,6 +14905,8 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ #endif PyTuple_SetItem(outTuple, paramCount, PyInt_FromLong(tmp_curr->ivalue)); + snprintf(messageStr, sizeof(messageStr), "Parameter %d: int value=%ld", paramCount, tmp_curr->ivalue); + LogMsg(DEBUG, messageStr, fileName); paramCount++; break; case SQL_REAL: @@ -11908,6 +14914,8 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ case SQL_DOUBLE: PyTuple_SetItem(outTuple, paramCount, PyFloat_FromDouble(tmp_curr->fvalue)); + snprintf(messageStr, sizeof(messageStr), "Parameter %d: float value=%f", paramCount, tmp_curr->fvalue); + LogMsg(DEBUG, messageStr, fileName); paramCount++; break; case SQL_TYPE_DATE: @@ -11917,6 +14925,8 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ PyDate_FromDate(tmp_curr->date_value->year, tmp_curr->date_value->month, tmp_curr->date_value->day)); + snprintf(messageStr, sizeof(messageStr), "Parameter %d: date value=%d-%02d-%02d", paramCount, tmp_curr->date_value->year, tmp_curr->date_value->month, tmp_curr->date_value->day); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -11932,6 +14942,8 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ PyTime_FromTime(tmp_curr->time_value->hour % 24, tmp_curr->time_value->minute, tmp_curr->time_value->second, 0)); + snprintf(messageStr, sizeof(messageStr), "Parameter %d: time value=%02d:%02d:%02d", paramCount, tmp_curr->time_value->hour % 24, tmp_curr->time_value->minute, tmp_curr->time_value->second); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -11950,6 +14962,8 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ tmp_curr->ts_value->minute, tmp_curr->ts_value->second, tmp_curr->ts_value->fraction / 1000)); + snprintf(messageStr, sizeof(messageStr), "Parameter %d: timestamp value=%d-%02d-%02d %02d:%02d:%02d.%03d", paramCount, tmp_curr->ts_value->year, tmp_curr->ts_value->month, tmp_curr->ts_value->day, tmp_curr->ts_value->hour % 24, tmp_curr->ts_value->minute, tmp_curr->ts_value->second, tmp_curr->ts_value->fraction / 1000); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -11964,6 +14978,8 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ PyTuple_SetItem( outTuple, paramCount, PyLong_FromString(tmp_curr->svalue, NULL, 0)); + snprintf(messageStr, sizeof(messageStr), "Parameter %d: bigint value=%s", paramCount, tmp_curr->svalue); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -11977,6 +14993,8 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ { PyTuple_SetItem( outTuple, paramCount, PyBytes_FromString(tmp_curr->svalue)); + snprintf(messageStr, sizeof(messageStr), "Parameter %d: blob value=%s", paramCount, tmp_curr->svalue); + LogMsg(DEBUG, messageStr, fileName); } else { @@ -11989,13 +15007,20 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ default: if (!NIL_P(tmp_curr->svalue)) { PyTuple_SetItem(outTuple, paramCount, StringOBJ_FromASCII(tmp_curr->svalue)); + snprintf(messageStr, sizeof(messageStr), "Parameter %d: String value = %s", paramCount, tmp_curr->svalue); + LogMsg(DEBUG, messageStr, fileName); paramCount++; } else if (!NIL_P(tmp_curr->uvalue)) { + PyObject *unicode_value = getSQLWCharAsPyUnicodeObject(tmp_curr->uvalue, tmp_curr->bind_indicator); PyTuple_SetItem(outTuple, paramCount, getSQLWCharAsPyUnicodeObject(tmp_curr->uvalue, tmp_curr->bind_indicator)); + snprintf(messageStr, sizeof(messageStr), "Parameter %d: Unicode value = %s", paramCount, PyUnicode_AsUTF8(unicode_value)); + LogMsg(DEBUG, messageStr, fileName); paramCount++; } else { Py_INCREF(Py_None); PyTuple_SetItem(outTuple, paramCount, Py_None); + snprintf(messageStr, sizeof(messageStr), "Parameter %d: None (no value)", paramCount); + LogMsg(DEBUG, messageStr, fileName); paramCount++; } break; @@ -12003,6 +15028,8 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ } else { Py_INCREF(Py_None); PyTuple_SetItem(outTuple, paramCount, Py_None); + snprintf(messageStr, sizeof(messageStr), "Parameter %d: None (SQL_NULL_DATA or SQL_NO_TOTAL)", paramCount); + LogMsg(DEBUG, messageStr, fileName); paramCount++; } tmp_curr = tmp_curr->next; @@ -12011,10 +15038,15 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ outTuple = (PyObject *)stmt_res; } } else { + LogMsg(ERROR, "Unexpected NULL stmt_res. Cannot return statement result.", fileName); + LogMsg(INFO, "exit callproc()", fileName); return NULL; } + LogMsg(DEBUG, "Parameters processed successfully. Returning result tuple", fileName); + LogMsg(INFO, "exit callproc()", fileName); return outTuple; } else { + LogMsg(ERROR, "Connection Resource invalid or procedure name is NULL", fileName); PyErr_SetString(PyExc_Exception, "Connection Resource invalid or procedure name is NULL"); return NULL; } @@ -12030,6 +15062,10 @@ static PyObject* ibm_db_callproc(PyObject *self, PyObject *args){ */ static PyObject* ibm_db_check_function_support(PyObject *self, PyObject *args) { + LogMsg(INFO, "entry check_function_support()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); PyObject *py_conn_res = NULL; PyObject *py_funtion_id = NULL; int funtion_id = 0; @@ -12038,26 +15074,35 @@ static PyObject* ibm_db_check_function_support(PyObject *self, PyObject *args) int rc = 0; if (!PyArg_ParseTuple(args, "OO", &py_conn_res, &py_funtion_id)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; } - + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_conn_res=%p, py_funtion_id=%p", py_conn_res, py_funtion_id); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_conn_res)) { if (!PyObject_TypeCheck(py_conn_res, &conn_handleType)) { + LogMsg(ERROR, "Supplied connection object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied connection object Parameter is invalid" ); return NULL; } else { conn_res = (conn_handle *)py_conn_res; + snprintf(messageStr, sizeof(messageStr), "Connection handle is valid. conn_res=%p", conn_res); + LogMsg(DEBUG, messageStr, fileName); } if (!NIL_P(py_funtion_id)) { if (PyInt_Check(py_funtion_id)){ - funtion_id = (int) PyInt_AsLong(py_funtion_id); + funtion_id = (int) PyLong_AsLong(py_funtion_id); + snprintf(messageStr, sizeof(messageStr), "Function ID parsed: funtion_id=%d", funtion_id); + LogMsg(DEBUG, messageStr, fileName); } else { + LogMsg(ERROR, "Supplied function ID parameter is invalid", fileName); PyErr_SetString(PyExc_Exception, "Supplied parameter is invalid"); return NULL; } } /* Check to ensure the connection resource given is active */ if (!conn_res->handle_active) { + LogMsg(ERROR, "Connection is not active", fileName); PyErr_SetString(PyExc_Exception, "Connection is not active"); return NULL; } @@ -12065,20 +15110,26 @@ static PyObject* ibm_db_check_function_support(PyObject *self, PyObject *args) Py_BEGIN_ALLOW_THREADS; rc = SQLGetFunctions(conn_res->hdbc, (SQLUSMALLINT) funtion_id, (SQLUSMALLINT*) &supported); Py_END_ALLOW_THREADS; - + snprintf(messageStr, sizeof(messageStr), "Called SQLGetFunctions with parameters: ConnectionHandle=%p, FunctionID=%d, and returned rc=%d, supported=%d", + conn_res->hdbc, funtion_id, rc, supported); + LogMsg(DEBUG, messageStr, fileName); if (rc == SQL_ERROR) { + LogMsg(INFO, "exit check_function_support()", fileName); Py_RETURN_FALSE; } else { if(supported == SQL_TRUE) { + LogMsg(INFO, "exit check_function_support()", fileName); Py_RETURN_TRUE; } else { + LogMsg(INFO, "exit check_function_support()", fileName); Py_RETURN_FALSE; } } } + LogMsg(INFO, "exit check_function_support()", fileName); return NULL; } @@ -12104,6 +15155,10 @@ static PyObject* ibm_db_check_function_support(PyObject *self, PyObject *args) */ PyObject *ibm_db_get_last_serial_value(int argc, PyObject *args, PyObject *self) { + LogMsg(INFO, "entry get_last_serial_value()", fileName); + PyObject *argsStr = PyObject_Repr(args); // Get string representation of args + snprintf(messageStr, sizeof(messageStr), "Received arguments: %s", PyUnicode_AsUTF8(argsStr)); + LogMsg(INFO, messageStr, fileName); SQLCHAR *value = NULL; SQLINTEGER pcbValue = 0; stmt_handle *stmt_res; @@ -12113,26 +15168,38 @@ PyObject *ibm_db_get_last_serial_value(int argc, PyObject *args, PyObject *self) PyObject *py_qualifier = NULL; PyObject *retVal = NULL; - if(!PyArg_ParseTuple(args, "O",&py_qualifier)) + if(!PyArg_ParseTuple(args, "O",&py_qualifier)) { + LogMsg(ERROR, "Failed to parse arguments", fileName); return NULL; - + } + snprintf(messageStr, sizeof(messageStr), "Parsed values: py_qualifier=%p", py_qualifier); + LogMsg(DEBUG, messageStr, fileName); if (!NIL_P(py_qualifier)) { if (!PyObject_TypeCheck(py_qualifier, &stmt_handleType)) { + LogMsg(ERROR, "Supplied statement object parameter is invalid", fileName); PyErr_SetString( PyExc_Exception, "Supplied statement object parameter is invalid" ); return NULL; } else { stmt_res = (stmt_handle *)py_qualifier; + snprintf(messageStr, sizeof(messageStr), "Statement handle is valid. stmt_res=%p", stmt_res); + LogMsg(DEBUG, messageStr, fileName); } /* We allocate a buffer of size 31 as per recommendations from the CLI IDS team */ value = ALLOC_N(char,31); if ( value == NULL ) { + LogMsg(ERROR, "Failed to allocate memory for value", fileName); PyErr_SetString(PyExc_Exception, "Failed to Allocate Memory"); return Py_False; } + snprintf(messageStr, sizeof(messageStr), "Calling SQLGetStmtAttr with parameters: hstmt=%p, attribute=%d, buffer_size=%d", + stmt_res->hstmt, SQL_ATTR_GET_GENERATED_VALUE, 31); + LogMsg(DEBUG, messageStr, fileName); Py_BEGIN_ALLOW_THREADS; rc = SQLGetStmtAttr((SQLHSTMT)stmt_res->hstmt, SQL_ATTR_GET_GENERATED_VALUE,(SQLPOINTER)value, 31,&pcbValue); Py_END_ALLOW_THREADS; + snprintf(messageStr, sizeof(messageStr), "SQLGetStmtAttr returned rc=%d, pcbValue=%d", rc, pcbValue); + LogMsg(DEBUG, messageStr, fileName); if ( rc == SQL_ERROR ) { _python_ibm_db_check_sql_errors( (SQLHSTMT)stmt_res->hstmt, SQL_HANDLE_STMT, rc, 1, NULL, -1, 1); if(value != NULL) { @@ -12142,14 +15209,19 @@ PyObject *ibm_db_get_last_serial_value(int argc, PyObject *args, PyObject *self) PyErr_Clear(); return Py_False; } + snprintf(messageStr, sizeof(messageStr), "Retrieved value: %s", (char *)value); + LogMsg(DEBUG, messageStr, fileName); retVal = StringOBJ_FromASCII((char *)value); if(value != NULL) { PyMem_Del(value); value = NULL; } + LogMsg(INFO, "exit get_last_serial_value()", fileName); return retVal; } else { + LogMsg(ERROR, "Supplied statement handle is invalid", fileName); + LogMsg(INFO, "exit get_last_serial_value()", fileName); PyErr_SetString(PyExc_Exception, "Supplied statement handle is invalid"); return Py_False; } @@ -12157,48 +15229,85 @@ PyObject *ibm_db_get_last_serial_value(int argc, PyObject *args, PyObject *self) static int _python_get_variable_type(PyObject *variable_value) { + LogMsg(INFO, "entry _python_get_variable_type()", fileName); if (PyBool_Check(variable_value) && (variable_value == Py_True)){ + LogMsg(INFO, "variable_value is a Py_True", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_TRUE", fileName); return PYTHON_TRUE; } else if (PyBool_Check(variable_value) && (variable_value == Py_False)){ + LogMsg(INFO, "variable_value is Py_False", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_FALSE", fileName); return PYTHON_FALSE; } else if (PyInt_Check(variable_value) || PyLong_Check(variable_value)){ + LogMsg(INFO, "variable_value is an integer", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_FIXNUM", fileName); return PYTHON_FIXNUM; } else if (PyFloat_Check(variable_value)){ + LogMsg(INFO, "variable_value is a float", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_FLOAT", fileName); return PYTHON_FLOAT; } else if (PyUnicode_Check(variable_value)){ + LogMsg(INFO, "variable_value is a Unicode string", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_UNICODE", fileName); return PYTHON_UNICODE; } else if (PyString_Check(variable_value) || PyBytes_Check(variable_value)){ + LogMsg(INFO, "variable_value is a string or bytes", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_STRING", fileName); return PYTHON_STRING; } else if (PyDateTime_Check(variable_value)){ + LogMsg(INFO, "variable_value is a datetime object", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_TIMESTAMP", fileName); return PYTHON_TIMESTAMP; } else if (PyTime_Check(variable_value)){ + LogMsg(INFO, "variable_value is a time object", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_TIME", fileName); return PYTHON_TIME; } else if (PyDate_Check(variable_value)){ + LogMsg(INFO, "variable_value is a date object", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_DATE", fileName); return PYTHON_DATE; } else if (PyComplex_Check(variable_value)){ + LogMsg(INFO, "variable_value is a complex number", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_COMPLEX", fileName); return PYTHON_COMPLEX; } else if (PyNumber_Check(variable_value)){ + LogMsg(INFO, "variable_value is a number", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_DECIMAL", fileName); return PYTHON_DECIMAL; } else if (PyList_Check(variable_value)){ - return PYTHON_LIST; - } + LogMsg(INFO, "variable_value is a list", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_LIST", fileName); + return PYTHON_LIST; + } else if (variable_value == Py_None){ + LogMsg(INFO, "variable_value is Py_None", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with PYTHON_NIL", fileName); return PYTHON_NIL; } - else return 0; + else { + LogMsg(INFO, "variable_value does not match any known type", fileName); + LogMsg(INFO, "exit _python_get_variable_type() with 0", fileName); + return 0; + } +} + +static PyObject* ibm_db_debug(PyObject* self, PyObject* args) { + _python_ibm_db_debug(self, args); + Py_RETURN_NONE; } + /* Listing of ibm_db module functions: */ static PyMethodDef ibm_db_Methods[] = { /* name, function, argument type, docstring */ @@ -12262,6 +15371,7 @@ static PyMethodDef ibm_db_Methods[] = { {"table_privileges", (PyCFunction)ibm_db_table_privileges, METH_VARARGS, "Returns a result set listing the tables and associated privileges in a database"}, {"tables", (PyCFunction)ibm_db_tables, METH_VARARGS, "Returns a result set listing the tables and associated metadata in a database"}, {"get_last_serial_value", (PyCFunction)ibm_db_get_last_serial_value, METH_VARARGS, "Returns last serial value inserted for identity column"}, + {"debug", (PyCFunction)ibm_db_debug, METH_VARARGS | METH_KEYWORDS, "Enable logging with optional log file or disable logging"}, /* An end-of-listing sentinel: */ {NULL, NULL, 0, NULL} }; diff --git a/ibmdb_tests.py b/ibmdb_tests.py index 090b4169..cfb31b82 100644 --- a/ibmdb_tests.py +++ b/ibmdb_tests.py @@ -6,6 +6,9 @@ import glob import config import importlib +# To log while testing +import ibm_db +ibm_db.debug("log.txt") _HTML_RUNNER = False