From: <nor...@t-...> - 2003-02-23 21:12:28
|
Hello, i've tested the driver again and found more little problems. This changes should solve the problems: //--------------------------------------- // file: OdbcConnection.cpp // I found a better way to solve the Disconnect-problem: // The function OdbcConnection::sqlDisconnect() keep unchanged (see my mail from yesterday - remove the changes). //--------------------------------------- OdbcConnection::~OdbcConnection() { if (connection) connection->close(); if (env) env->connectionClosed (this); // NOMEY begin while (statements) { OdbcStatement* statement = statements; statements = (OdbcStatement*)statement->next; delete statement; } while (descriptors) { OdbcDesc* descriptor = descriptors; descriptors = (OdbcDesc*)descriptor->next; delete descriptor; } // NOMEY end #ifdef ELF if (libraryHandle) dlclose (libraryHandle); #endif } //--------------------------------------- //--------------------------------------- // unchanged RETCODE OdbcConnection::sqlDisconnect() { if (!connected) sqlReturn (SQL_ERROR, "08003", "Connection does not exist"); if (transactionPending) sqlReturn (SQL_ERROR, "25000", "Invalid transaction state"); try { connection->commit(); connection->close(); connection = NULL; connected = false; } catch (SQLException& exception) { postError ("01002", exception); connection = NULL; connected = false; return SQL_SUCCESS_WITH_INFO; } return sqlSuccess(); } //--------------------------------------- //--------------------------------------- // file: IscConnection.cpp // Set statement->connection to NULL. This prevent connection->deleteStatement(this) // in destructor of IscStatement. //--------------------------------------- void IscConnection::close() { FOR_OBJECTS (IscStatement*, statement, &statements) statement->close(); + statement->connection = NULL; // NOMEY + END_FOR; delete this; } //--------------------------------------- //--------------------------------------- // file: OdbcObject.cpp // Initialize next //--------------------------------------- OdbcObject::OdbcObject() { + next = NULL; // NOMEY + errors = NULL; } //--------------------------------------- // // problems with sql-type DATE // //--------------------------------------- // file: IscStatement.cpp // SQL_TIMESTAMP and SQL_TYPE_DATE should be handled in the // same manner. //--------------------------------------- void IscStatement::setValue(Value *value, XSQLVAR *var) ... case SQL_TYPE_DATE: { ISC_DATE date = *(ISC_DATE*) var->sqldata; long days = date - baseDate; DateTime dateTime; -// dateTime = (long) (days * 24 * 60 * 60); // NOMEY- + dateTime = days; // NOMEY+ value->setValue (dateTime); } break; ... //--------------------------------------- //--------------------------------------- // file: DateTime.cpp // ... //--------------------------------------- signed long DateTime::decodeDate (signed long nday, tm *times) ... -// nday = nday / (60 * 60 * 24); // NOMEY - ... //--------------------------------------- //--------------------------------------- // file: OdbcDateTime.cpp // ... //--------------------------------------- int OdbcDateTime::convert (DateTime * dateTimeIn, tagDATE_STRUCT * tagDateOut) { struct tm timeBuffer; struct tm* times = &timeBuffer; memset (times, 0, sizeof (*times)); // ndate (dateTimeIn->date, times); // From B. Schulte -// ndate ((dateTimeIn->date / 24 /60/60),0, times); // NOMEY - + ndate (dateTimeIn->date,0, times); // NOMEY + times->tm_yday = yday (times); if ((times->tm_wday = ((dateTimeIn->date) + 3) % 7) < 0) times->tm_wday += 7; tagDateOut->year = times->tm_year + 1900; tagDateOut->month = times->tm_mon + 1; tagDateOut->day = times->tm_mday; return true; } //--------------------------------------- //--------------------------------------- // file: OdbcStatement.cpp // Parentheses missing //--------------------------------------- bool OdbcStatement::setValue(Binding * binding, int column) ... case SQL_C_TYPE_TIME: case SQL_C_TIME: { SqlTime sqlTime = RESULTS (getTime (column)); tagTIME_STRUCT *var = (tagTIME_STRUCT*) binding->pointer; -// var->hour = (unsigned short) (sqlTime.timeValue / 60 * 60) % 24; // NOMEY - + var->hour = (unsigned short) (sqlTime.timeValue / (60 * 60)) % 24; // NOMEY + var->minute = (unsigned short) (sqlTime.timeValue / 60) % 60; var->second = (unsigned short) (sqlTime.timeValue % 60); length = sizeof (tagTIME_STRUCT); } break; ... //--------------------------------------- //--------------------------------------- // file: OdbcStatement.cpp // test binding->indicatorPointer //--------------------------------------- RETCODE OdbcStatement::executeStatement() { parameterNeedData = -1; for (int n = 0; n < numberParameters; ++n) { Binding *binding = parameters + n; if ( ( binding->pointer || binding->indicatorPointer ) && binding->type != SQL_PARAM_OUTPUT ) -// if ( *binding->indicatorPointer == SQL_DATA_AT_EXEC || *binding->indicatorPointer < SQL_LEN_DATA_AT_EXEC_OFFSET ) // NOMEY - + if (binding->indicatorPointer &&( *binding->indicatorPointer == SQL_DATA_AT_EXEC || *binding->indicatorPointer < SQL_LEN_DATA_AT_EXEC_OFFSET )) // NOMEY + return SQL_NEED_DATA; else setParameter (binding, n + 1); } if (callableStatement) for (int n = 0; n < numberParameters; ++n) { Binding *binding = parameters + n; if (binding->pointer && binding->type != SQL_PARAM_INPUT) callableStatement->registerOutParameter (n + 1, binding->sqlType); } statement->execute(); connection->transactionStarted(); if (callableStatement) for (int n = 0; n < numberParameters; ++n) { Binding *binding = parameters + n; if (binding->pointer && binding->type != SQL_PARAM_INPUT) setValue (binding, n + 1); } getResultSet(); return SQL_SUCCESS; } //--------------------------------------- Best regards, Norbert! |