LCOV - code coverage report
Current view: top level - libreoffice/connectivity/source/drivers/odbcbase - OTools.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 0 308 0.0 %
Date: 2012-12-27 Functions: 0 14 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : #include "odbc/OTools.hxx"
      21             : #include "odbc/OFunctions.hxx"
      22             : #include <com/sun/star/sdbc/DataType.hpp>
      23             : #include <osl/diagnose.h>
      24             : #include "odbc/OConnection.hxx"
      25             : #include "diagnose_ex.h"
      26             : #include <rtl/logfile.hxx>
      27             : #include <rtl/ustrbuf.hxx>
      28             : #include <boost/static_assert.hpp>
      29             : 
      30             : 
      31             : #include <string.h>
      32             : #include <string>
      33             : #include <algorithm>
      34             : 
      35             : using namespace connectivity::odbc;
      36             : using namespace com::sun::star::uno;
      37             : using namespace com::sun::star::sdbc;
      38             : using namespace com::sun::star::util;
      39             : 
      40             : namespace {
      41           0 : size_t sqlTypeLen ( SQLSMALLINT _nType )
      42             : {
      43           0 :     switch (_nType)
      44             :     {
      45             :     case SQL_C_SSHORT:
      46             :     case SQL_C_SHORT:
      47           0 :         return sizeof(SQLSMALLINT);
      48             :     case SQL_C_USHORT:
      49           0 :         return sizeof(SQLUSMALLINT);
      50             :     case SQL_C_SLONG:
      51             :     case SQL_C_LONG:
      52           0 :         return sizeof(SQLINTEGER);
      53             :     case SQL_C_ULONG:
      54           0 :         return sizeof(SQLUINTEGER);
      55             :     case SQL_C_FLOAT:
      56           0 :         return sizeof(SQLREAL);
      57             :     case SQL_C_DOUBLE:
      58             :         OSL_ENSURE(sizeof(SQLDOUBLE) == sizeof(SQLFLOAT), "SQLDOUBLE/SQLFLOAT confusion");
      59           0 :         return sizeof(SQLDOUBLE);
      60             :     case SQL_C_BIT:
      61           0 :         return sizeof(SQLCHAR);
      62             :     case SQL_C_STINYINT:
      63             :     case SQL_C_TINYINT:
      64           0 :         return sizeof(SQLSCHAR);
      65             :     case SQL_C_UTINYINT:
      66           0 :         return sizeof(SQLCHAR);
      67             :     case SQL_C_SBIGINT:
      68           0 :         return sizeof(SQLBIGINT);
      69             :     case SQL_C_UBIGINT:
      70           0 :         return sizeof(SQLUBIGINT);
      71             :     /* UnixODBC gives this the same value as SQL_C_UBIGINT
      72             :     case SQL_C_BOOKMARK:
      73             :         return sizeof(BOOKMARK); */
      74             :     case SQL_C_TYPE_DATE:
      75             :     case SQL_C_DATE:
      76           0 :         return sizeof(SQL_DATE_STRUCT);
      77             :     case SQL_C_TYPE_TIME:
      78             :     case SQL_C_TIME:
      79           0 :         return sizeof(SQL_TIME_STRUCT);
      80             :     case SQL_C_TYPE_TIMESTAMP:
      81             :     case SQL_C_TIMESTAMP:
      82           0 :         return sizeof(SQL_TIMESTAMP_STRUCT);
      83             :     case SQL_C_NUMERIC:
      84           0 :         return sizeof(SQL_NUMERIC_STRUCT);
      85             :     case SQL_C_GUID:
      86           0 :         return sizeof(SQLGUID);
      87             :     case SQL_C_INTERVAL_YEAR:
      88             :     case SQL_C_INTERVAL_MONTH:
      89             :     case SQL_C_INTERVAL_DAY:
      90             :     case SQL_C_INTERVAL_HOUR:
      91             :     case SQL_C_INTERVAL_MINUTE:
      92             :     case SQL_C_INTERVAL_SECOND:
      93             :     case SQL_C_INTERVAL_YEAR_TO_MONTH:
      94             :     case SQL_C_INTERVAL_DAY_TO_HOUR:
      95             :     case SQL_C_INTERVAL_DAY_TO_MINUTE:
      96             :     case SQL_C_INTERVAL_DAY_TO_SECOND:
      97             :     case SQL_C_INTERVAL_HOUR_TO_MINUTE:
      98             :     case SQL_C_INTERVAL_HOUR_TO_SECOND:
      99             :     case SQL_C_INTERVAL_MINUTE_TO_SECOND:
     100           0 :         return sizeof(SQL_INTERVAL_STRUCT);
     101             :     // ** Variable-sized datatypes -> cannot predict length
     102             :     case SQL_C_CHAR:
     103             :     case SQL_C_WCHAR:
     104             :     case SQL_C_BINARY:
     105             :     // UnixODBC gives this the same value as SQL_C_BINARY
     106             :     //case SQL_C_VARBOOKMARK:
     107             :     // Unknown datatype -> cannot predict length
     108             :     default:
     109           0 :         return static_cast<size_t>(-1);
     110             :     }
     111             : }
     112             : }
     113             : 
     114             : 
     115           0 : void OTools::getValue(  OConnection* _pConnection,
     116             :                         SQLHANDLE _aStatementHandle,
     117             :                         sal_Int32 columnIndex,
     118             :                         SQLSMALLINT _nType,
     119             :                         sal_Bool &_bWasNull,
     120             :                         const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface >& _xInterface,
     121             :                         void* _pValue,
     122             :                         SQLLEN _nSize) throw(::com::sun::star::sdbc::SQLException, ::com::sun::star::uno::RuntimeException)
     123             : {
     124             :     RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "odbc", "Ocke.Janssen@sun.com", "OTools::getValue" );
     125           0 :     const size_t properSize = sqlTypeLen(_nType);
     126           0 :     if ( properSize == static_cast<size_t>(-1) )
     127             :         OSL_FAIL("connectivity::odbc::OTools::getValue: unknown SQL type - cannot check buffer size");
     128             :     else
     129             :     {
     130             :         OSL_ENSURE(static_cast<size_t>(_nSize) == properSize, "connectivity::odbc::OTools::getValue got wrongly sized memory region to write result to");
     131           0 :         if ( static_cast<size_t>(_nSize) > properSize )
     132             :         {
     133             :             OSL_FAIL("memory region is too big - trying to fudge it");
     134           0 :             memset(_pValue, 0, _nSize);
     135             : #ifdef OSL_BIGENDIAN
     136             :             // This is skewed in favour of integer types
     137             :             _pValue += _nSize - properSize;
     138             : #endif
     139             :         }
     140             :     }
     141             :     OSL_ENSURE(static_cast<size_t>(_nSize) >= properSize, "memory region is too small");
     142           0 :     SQLLEN pcbValue = SQL_NULL_DATA;
     143             :     OTools::ThrowException(_pConnection,
     144           0 :                             (*(T3SQLGetData)_pConnection->getOdbcFunction(ODBC3SQLGetData))(_aStatementHandle,
     145             :                                         (SQLUSMALLINT)columnIndex,
     146             :                                         _nType,
     147             :                                         _pValue,
     148             :                                         _nSize,
     149           0 :                                         &pcbValue),
     150           0 :                             _aStatementHandle,SQL_HANDLE_STMT,_xInterface,sal_False);
     151           0 :     _bWasNull = pcbValue == SQL_NULL_DATA;
     152           0 : }
     153             : // -------------------------------------------------------------------------
     154           0 : void OTools::bindValue( OConnection* _pConnection,
     155             :                         SQLHANDLE _aStatementHandle,
     156             :                         sal_Int32 columnIndex,
     157             :                         SQLSMALLINT _nType,
     158             :                         SQLSMALLINT _nMaxLen,
     159             :                         const void* _pValue,
     160             :                         void* _pData,
     161             :                         SQLLEN * const pLen,
     162             :                         const ::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface >& _xInterface,
     163             :                         rtl_TextEncoding _nTextEncoding,
     164             :                         sal_Bool _bUseOldTimeDate) throw(::com::sun::star::sdbc::SQLException, ::com::sun::star::uno::RuntimeException)
     165             : {
     166             :     RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "odbc", "Ocke.Janssen@sun.com", "OTools::bindValue" );
     167             :     SQLRETURN nRetcode;
     168             :     SQLSMALLINT   fSqlType;
     169             :     SQLSMALLINT   fCType;
     170           0 :     SQLLEN nMaxLen = _nMaxLen;
     171             : 
     172             :     OTools::getBindTypes(   sal_False,
     173             :                             _bUseOldTimeDate,
     174             :                             _nType,
     175             :                             fCType,
     176           0 :                             fSqlType);
     177             : 
     178           0 :     if (columnIndex != 0 && !_pValue)
     179             :     {
     180           0 :         *pLen = SQL_NULL_DATA;
     181           0 :         nRetcode = (*(T3SQLBindCol)_pConnection->getOdbcFunction(ODBC3SQLBindCol))(_aStatementHandle,
     182             :                                 (SQLUSMALLINT)columnIndex,
     183             :                                 fCType,
     184             :                                 _pData,
     185             :                                 nMaxLen,
     186             :                                 pLen
     187           0 :                                 );
     188             :     }
     189             :     else
     190             :     {
     191             :         try
     192             :         {
     193           0 :             switch (_nType)
     194             :             {
     195             :                 case SQL_CHAR:
     196             :                 case SQL_VARCHAR:
     197             :                 {
     198           0 :                     ::rtl::OString aString(::rtl::OUStringToOString(*(::rtl::OUString*)_pValue,_nTextEncoding));
     199           0 :                     *pLen = SQL_NTS;
     200           0 :                     *((::rtl::OString*)_pData) = aString;
     201           0 :                     _nMaxLen = (SQLSMALLINT)aString.getLength();
     202             : 
     203             :                     // Pointer on Char*
     204           0 :                     _pData = (void*)aString.getStr();
     205           0 :                 }   break;
     206             :                 case SQL_BIGINT:
     207           0 :                     *((sal_Int64*)_pData) = *(sal_Int64*)_pValue;
     208           0 :                     *pLen = sizeof(sal_Int64);
     209           0 :                     break;
     210             :                 case SQL_DECIMAL:
     211             :                 case SQL_NUMERIC:
     212             :                 {
     213           0 :                     ::rtl::OString aString = ::rtl::OString::valueOf(*(double*)_pValue);
     214           0 :                     _nMaxLen = (SQLSMALLINT)aString.getLength();
     215           0 :                     *pLen = _nMaxLen;
     216           0 :                     *((::rtl::OString*)_pData) = aString;
     217             :                     // Pointer on Char*
     218           0 :                     _pData = (void*)((::rtl::OString*)_pData)->getStr();
     219           0 :                 }   break;
     220             :                 case SQL_BIT:
     221             :                 case SQL_TINYINT:
     222           0 :                     *((sal_Int8*)_pData) = *(sal_Int8*)_pValue;
     223           0 :                     *pLen = sizeof(sal_Int8);
     224           0 :                     break;
     225             : 
     226             :                 case SQL_SMALLINT:
     227           0 :                     *((sal_Int16*)_pData) = *(sal_Int16*)_pValue;
     228           0 :                     *pLen = sizeof(sal_Int16);
     229           0 :                     break;
     230             :                 case SQL_INTEGER:
     231           0 :                     *((sal_Int32*)_pData) = *(sal_Int32*)_pValue;
     232           0 :                     *pLen = sizeof(sal_Int32);
     233           0 :                     break;
     234             :                 case SQL_FLOAT:
     235           0 :                     *((float*)_pData) = *(float*)_pValue;
     236           0 :                     *pLen = sizeof(float);
     237           0 :                     break;
     238             :                 case SQL_REAL:
     239             :                 case SQL_DOUBLE:
     240           0 :                     *((double*)_pData) = *(double*)_pValue;
     241           0 :                     *pLen = sizeof(double);
     242           0 :                     break;
     243             :                 case SQL_BINARY:
     244             :                 case SQL_VARBINARY:
     245             :                     {
     246           0 :                         _pData = (void*)((const ::com::sun::star::uno::Sequence< sal_Int8 > *)_pValue)->getConstArray();
     247           0 :                         *pLen = ((const ::com::sun::star::uno::Sequence< sal_Int8 > *)_pValue)->getLength();
     248           0 :                     }   break;
     249             :                 case SQL_LONGVARBINARY:
     250             :                 {
     251           0 :                     _pData = (void*)(sal_IntPtr)(columnIndex);
     252           0 :                     sal_Int32 nLen = 0;
     253           0 :                     nLen = ((const ::com::sun::star::uno::Sequence< sal_Int8 > *)_pValue)->getLength();
     254           0 :                     *pLen = (SQLLEN)SQL_LEN_DATA_AT_EXEC(nLen);
     255             :                 }
     256           0 :                     break;
     257             :                 case SQL_LONGVARCHAR:
     258             :                 {
     259           0 :                     _pData = (void*)(sal_IntPtr)(columnIndex);
     260           0 :                     sal_Int32 nLen = 0;
     261           0 :                     nLen = ((::rtl::OUString*)_pValue)->getLength();
     262           0 :                     *pLen = (SQLLEN)SQL_LEN_DATA_AT_EXEC(nLen);
     263           0 :                 }   break;
     264             :                 case SQL_DATE:
     265           0 :                     *pLen = sizeof(DATE_STRUCT);
     266           0 :                     *((DATE_STRUCT*)_pData) = *(DATE_STRUCT*)_pValue;
     267           0 :                     break;
     268             :                 case SQL_TIME:
     269           0 :                     *pLen = sizeof(TIME_STRUCT);
     270           0 :                     *((TIME_STRUCT*)_pData) = *(TIME_STRUCT*)_pValue;
     271           0 :                     break;
     272             :                 case SQL_TIMESTAMP:
     273           0 :                     *pLen = sizeof(TIMESTAMP_STRUCT);
     274           0 :                     *((TIMESTAMP_STRUCT*)_pData) = *(TIMESTAMP_STRUCT*)_pValue;
     275           0 :                     break;
     276             :             }
     277             :         }
     278           0 :         catch ( ... )
     279             :         {
     280             :         }
     281             : 
     282           0 :         nRetcode = (*(T3SQLBindCol)_pConnection->getOdbcFunction(ODBC3SQLBindCol))(_aStatementHandle,
     283             :                                 (SQLUSMALLINT)columnIndex,
     284             :                                 fCType,
     285             :                                 _pData,
     286             :                                 nMaxLen,
     287             :                                 pLen
     288           0 :                                 );
     289             :     }
     290             : 
     291           0 :     OTools::ThrowException(_pConnection,nRetcode,_aStatementHandle,SQL_HANDLE_STMT,_xInterface);
     292           0 : }
     293             : // -----------------------------------------------------------------------------
     294           0 : void OTools::ThrowException(const OConnection* _pConnection,
     295             :                             const SQLRETURN _rRetCode,
     296             :                             const SQLHANDLE _pContext,
     297             :                             const SQLSMALLINT _nHandleType,
     298             :                             const Reference< XInterface >& _xInterface,
     299             :                             const sal_Bool _bNoFound,
     300             :                             const rtl_TextEncoding _nTextEncoding) throw(SQLException)
     301             : {
     302           0 :     switch(_rRetCode)
     303             :     {
     304             :         case SQL_NEED_DATA:
     305             :         case SQL_STILL_EXECUTING:
     306             :         case SQL_SUCCESS:
     307             : 
     308             :         case SQL_SUCCESS_WITH_INFO:
     309             :                         return;
     310             :         case SQL_NO_DATA_FOUND:
     311           0 :                                 if(_bNoFound)
     312             :                                     return; // no need to throw a exception
     313           0 :         case SQL_ERROR:             break;
     314             : 
     315             : 
     316             :         case SQL_INVALID_HANDLE:    OSL_FAIL("SdbODBC3_SetStatus: SQL_INVALID_HANDLE");
     317           0 :                                     throw SQLException();
     318             :     }
     319             : 
     320             :     // Additional Information on the latest ODBC-functioncall available
     321             :     // SQLError provides this Information.
     322             :     RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "odbc", "Ocke.Janssen@sun.com", "OTools::ThrowException" );
     323             : 
     324             :     SDB_ODBC_CHAR szSqlState[5];
     325             :     SQLINTEGER pfNativeError;
     326             :     SDB_ODBC_CHAR szErrorMessage[SQL_MAX_MESSAGE_LENGTH];
     327           0 :     szErrorMessage[0] = '\0';
     328           0 :     SQLSMALLINT pcbErrorMsg = 0;
     329             : 
     330             :     // Information for latest operation:
     331             :     // when hstmt != SQL_NULL_HSTMT is (Used from SetStatus in SdbCursor, SdbTable, ...),
     332             :     // then the status of the latest statments will be fetched, without the Status of the last
     333             :     // Statments of this connection [what in this case will probably be the same, but the Reference
     334             :     // Manual isn't totally clear in this...].
     335             :     // corresponding for hdbc.
     336           0 :     SQLRETURN n = (*(T3SQLGetDiagRec)_pConnection->getOdbcFunction(ODBC3SQLGetDiagRec))(_nHandleType,_pContext,1,
     337             :                          szSqlState,
     338             :                          &pfNativeError,
     339           0 :                          szErrorMessage,sizeof szErrorMessage - 1,&pcbErrorMsg);
     340             :     OSL_UNUSED( n );
     341             :     OSL_ENSURE(n != SQL_INVALID_HANDLE,"SdbODBC3_SetStatus: SQLError returned SQL_INVALID_HANDLE");
     342             :     OSL_ENSURE(n == SQL_SUCCESS || n == SQL_SUCCESS_WITH_INFO || n == SQL_NO_DATA_FOUND || n == SQL_ERROR,"SdbODBC3_SetStatus: SQLError failed");
     343             : 
     344             :     // For the Return Code of SQLError see ODBC 2.0 Programmer's Reference Page 287ff
     345             :     throw SQLException( ::rtl::OUString((char *)szErrorMessage,pcbErrorMsg,_nTextEncoding),
     346             :                                     _xInterface,
     347             :                                     ::rtl::OUString((char *)szSqlState,5,_nTextEncoding),
     348             :                                     pfNativeError,
     349             :                                     Any()
     350           0 :                                 );
     351             : 
     352             : }
     353             : // -------------------------------------------------------------------------
     354           0 : Sequence<sal_Int8> OTools::getBytesValue(const OConnection* _pConnection,
     355             :                                          const SQLHANDLE _aStatementHandle,
     356             :                                          const sal_Int32 columnIndex,
     357             :                                          const SQLSMALLINT _fSqlType,
     358             :                                          sal_Bool &_bWasNull,
     359             :                                          const Reference< XInterface >& _xInterface) throw(SQLException, RuntimeException)
     360             : {
     361             :     RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "odbc", "Ocke.Janssen@sun.com", "OTools::getBytesValue" );
     362             :     sal_Int8 aCharArray[2048];
     363             :     // First try to fetch the data with the little Buffer:
     364           0 :     const SQLLEN nMaxLen = sizeof aCharArray;
     365           0 :     SQLLEN pcbValue = SQL_NO_TOTAL;
     366           0 :     Sequence<sal_Int8> aData;
     367             : 
     368             :     // >= because if the data is nMaxLen long, our buffer is actually ONE byte short,
     369             :     // for the null byte terminator!
     370           0 :     while (pcbValue == SQL_NO_TOTAL || pcbValue >= nMaxLen)
     371             :     {
     372             :         OTools::ThrowException(_pConnection,
     373           0 :                                (*(T3SQLGetData)_pConnection->getOdbcFunction(ODBC3SQLGetData))(
     374             :                                    _aStatementHandle,
     375             :                                    (SQLUSMALLINT)columnIndex,
     376             :                                    _fSqlType,
     377             :                                    (SQLPOINTER)aCharArray,
     378             :                                    nMaxLen,
     379           0 :                                    &pcbValue),
     380           0 :                                _aStatementHandle,SQL_HANDLE_STMT,_xInterface);
     381             : 
     382           0 :         _bWasNull = pcbValue == SQL_NULL_DATA;
     383           0 :         if(_bWasNull)
     384           0 :             return Sequence<sal_Int8>();
     385             : 
     386             :         SQLLEN nReadBytes;
     387             :         // After the SQLGetData that wrote out to aCharArray the last byte of the data,
     388             :         // pcbValue will not be SQL_NO_TOTAL -> we have a reliable count
     389           0 :         if ( (pcbValue == SQL_NO_TOTAL) || (pcbValue >= nMaxLen) )
     390             :         {
     391             :             // we filled the buffer; remove the terminating null byte
     392           0 :             nReadBytes = nMaxLen-1;
     393           0 :             if ( aCharArray[nReadBytes] != 0)
     394             :             {
     395             :                 OSL_FAIL("Buggy ODBC driver? Did not null-terminate (variable length) data!");
     396           0 :                 ++nReadBytes;
     397             :             }
     398             :         }
     399             :         else
     400             :         {
     401           0 :             nReadBytes = pcbValue;
     402             :         }
     403           0 :         const sal_Int32 nLen = aData.getLength();
     404           0 :         aData.realloc(nLen + nReadBytes);
     405           0 :         memcpy(aData.getArray() + nLen, aCharArray, nReadBytes);
     406             :     }
     407           0 :     return aData;
     408             : }
     409             : // -------------------------------------------------------------------------
     410           0 : ::rtl::OUString OTools::getStringValue(OConnection* _pConnection,
     411             :                                        SQLHANDLE _aStatementHandle,
     412             :                                        sal_Int32 columnIndex,
     413             :                                        SQLSMALLINT _fSqlType,
     414             :                                        sal_Bool &_bWasNull,
     415             :                                        const Reference< XInterface >& _xInterface,
     416             :                                        rtl_TextEncoding _nTextEncoding) throw(SQLException, RuntimeException)
     417             : {
     418             :     RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "odbc", "Ocke.Janssen@sun.com", "OTools::getStringValue" );
     419           0 :     ::rtl::OUStringBuffer aData;
     420           0 :     switch(_fSqlType)
     421             :     {
     422             :     case SQL_WVARCHAR:
     423             :     case SQL_WCHAR:
     424             :     case SQL_WLONGVARCHAR:
     425             :     {
     426             :         sal_Unicode waCharArray[2048];
     427             :         // we assume everyone (LibO & ODBC) uses UTF-16; see OPreparedStatement::setParameter
     428             :         BOOST_STATIC_ASSERT(sizeof(sal_Unicode) == 2);
     429             :         BOOST_STATIC_ASSERT(sizeof(SQLWCHAR)    == 2);
     430             :         // read the unicode data
     431           0 :         const SQLLEN nMaxLen = sizeof(waCharArray) / sizeof(sal_Unicode);
     432           0 :         SQLLEN pcbValue = SQL_NO_TOTAL;
     433             : 
     434           0 :         while ((pcbValue == SQL_NO_TOTAL ) || (pcbValue >= nMaxLen) )
     435             :         {
     436             :             OTools::ThrowException(_pConnection,
     437           0 :                                    (*(T3SQLGetData)_pConnection->getOdbcFunction(ODBC3SQLGetData))(
     438             :                                        _aStatementHandle,
     439             :                                        (SQLUSMALLINT)columnIndex,
     440             :                                        SQL_C_WCHAR,
     441             :                                        &waCharArray,
     442             :                                        (SQLLEN)nMaxLen*sizeof(sal_Unicode),
     443           0 :                                        &pcbValue),
     444           0 :                                    _aStatementHandle,SQL_HANDLE_STMT,_xInterface);
     445           0 :             _bWasNull = pcbValue == SQL_NULL_DATA;
     446           0 :             if(_bWasNull)
     447           0 :                 return ::rtl::OUString();
     448             : 
     449             :             SQLLEN nReadChars;
     450           0 :             if ( (pcbValue == SQL_NO_TOTAL) || (pcbValue >= nMaxLen) )
     451             :             {
     452             :                 // we filled the buffer; remove the terminating null character
     453           0 :                 nReadChars = nMaxLen-1;
     454           0 :                 if ( waCharArray[nReadChars] != 0)
     455             :                 {
     456             :                     OSL_FAIL("Buggy ODBC driver? Did not null-terminate (variable length) data!");
     457           0 :                     ++nReadChars;
     458             :                 }
     459             :             }
     460             :             else
     461             :             {
     462           0 :                 nReadChars = pcbValue;
     463             :             }
     464             : 
     465           0 :             aData.append(waCharArray, nReadChars);
     466             : 
     467             :         }
     468             :         break;
     469             :     }
     470             :     default:
     471             :     {
     472             :         char aCharArray[2048];
     473             :         // read the unicode data
     474           0 :         const SQLLEN nMaxLen = sizeof(aCharArray);
     475           0 :         SQLLEN pcbValue = SQL_NO_TOTAL;
     476             : 
     477           0 :         while ((pcbValue == SQL_NO_TOTAL ) || (pcbValue >= nMaxLen) )
     478             :         {
     479             :             OTools::ThrowException(_pConnection,
     480           0 :                                    (*(T3SQLGetData)_pConnection->getOdbcFunction(ODBC3SQLGetData))(
     481             :                                        _aStatementHandle,
     482             :                                        (SQLUSMALLINT)columnIndex,
     483             :                                        SQL_C_CHAR,
     484             :                                        &aCharArray,
     485             :                                        nMaxLen,
     486           0 :                                        &pcbValue),
     487           0 :                                    _aStatementHandle,SQL_HANDLE_STMT,_xInterface);
     488           0 :             _bWasNull = pcbValue == SQL_NULL_DATA;
     489           0 :             if(_bWasNull)
     490           0 :                 return ::rtl::OUString();
     491             : 
     492             :             SQLLEN nReadChars;
     493           0 :             if ( (pcbValue == SQL_NO_TOTAL) || (pcbValue >= nMaxLen) )
     494             :             {
     495             :                 // we filled the buffer; remove the terminating null character
     496           0 :                 nReadChars = nMaxLen-1;
     497           0 :                 if ( aCharArray[nReadChars] != 0)
     498             :                 {
     499             :                     OSL_FAIL("Buggy ODBC driver? Did not null-terminate (variable length) data!");
     500           0 :                     ++nReadChars;
     501             :                 }
     502             :             }
     503             :             else
     504             :             {
     505           0 :                 nReadChars = pcbValue;
     506             :             }
     507             : 
     508           0 :             aData.append(::rtl::OUString(aCharArray, nReadChars, _nTextEncoding));
     509             : 
     510             :         }
     511             :         break;
     512             :     }
     513             :     }
     514             : 
     515           0 :     return aData.makeStringAndClear();
     516             : }
     517             : // -------------------------------------------------------------------------
     518           0 : void OTools::GetInfo(OConnection* _pConnection,
     519             :                      SQLHANDLE _aConnectionHandle,
     520             :                      SQLUSMALLINT _nInfo,
     521             :                      ::rtl::OUString &_rValue,
     522             :                      const Reference< XInterface >& _xInterface,
     523             :                      rtl_TextEncoding _nTextEncoding) throw(SQLException, RuntimeException)
     524             : {
     525             :     char aValue[512];
     526           0 :     SQLSMALLINT nValueLen=0;
     527             :     OTools::ThrowException(_pConnection,
     528           0 :         (*(T3SQLGetInfo)_pConnection->getOdbcFunction(ODBC3SQLGetInfo))(_aConnectionHandle,_nInfo,aValue,(sizeof aValue)-1,&nValueLen),
     529           0 :         _aConnectionHandle,SQL_HANDLE_DBC,_xInterface);
     530             : 
     531           0 :     _rValue = ::rtl::OUString(aValue,nValueLen,_nTextEncoding);
     532           0 : }
     533             : // -------------------------------------------------------------------------
     534           0 : void OTools::GetInfo(OConnection* _pConnection,
     535             :                      SQLHANDLE _aConnectionHandle,
     536             :                      SQLUSMALLINT _nInfo,
     537             :                      sal_Int32 &_rValue,
     538             :                      const Reference< XInterface >& _xInterface) throw(SQLException, RuntimeException)
     539             : {
     540             :     SQLSMALLINT nValueLen;
     541           0 :     _rValue = 0;    // in case the driver uses only 16 of the 32 bits (as it does, for example, for SQL_CATALOG_LOCATION)
     542             :     OTools::ThrowException(_pConnection,
     543           0 :         (*(T3SQLGetInfo)_pConnection->getOdbcFunction(ODBC3SQLGetInfo))(_aConnectionHandle,_nInfo,&_rValue,sizeof _rValue,&nValueLen),
     544           0 :         _aConnectionHandle,SQL_HANDLE_DBC,_xInterface);
     545           0 : }
     546             : // -------------------------------------------------------------------------
     547           0 : void OTools::GetInfo(OConnection* _pConnection,
     548             :                      SQLHANDLE _aConnectionHandle,
     549             :                      SQLUSMALLINT _nInfo,
     550             :                      SQLUINTEGER &_rValue,
     551             :                      const Reference< XInterface >& _xInterface) throw(SQLException, RuntimeException)
     552             : {
     553             :     SQLSMALLINT nValueLen;
     554           0 :     _rValue = 0;    // in case the driver uses only 16 of the 32 bits (as it does, for example, for SQL_CATALOG_LOCATION)
     555             :     OTools::ThrowException(_pConnection,
     556           0 :         (*(T3SQLGetInfo)_pConnection->getOdbcFunction(ODBC3SQLGetInfo))(_aConnectionHandle,_nInfo,&_rValue,sizeof _rValue,&nValueLen),
     557           0 :         _aConnectionHandle,SQL_HANDLE_DBC,_xInterface);
     558           0 : }
     559             : // -------------------------------------------------------------------------
     560           0 : void OTools::GetInfo(OConnection* _pConnection,
     561             :                      SQLHANDLE _aConnectionHandle,
     562             :                      SQLUSMALLINT _nInfo,
     563             :                      SQLUSMALLINT &_rValue,
     564             :                      const Reference< XInterface >& _xInterface) throw(SQLException, RuntimeException)
     565             : {
     566             :     SQLSMALLINT nValueLen;
     567           0 :     _rValue = 0;    // in case the driver uses only 16 of the 32 bits (as it does, for example, for SQL_CATALOG_LOCATION)
     568             :     OTools::ThrowException(_pConnection,
     569           0 :         (*(T3SQLGetInfo)_pConnection->getOdbcFunction(ODBC3SQLGetInfo))(_aConnectionHandle,_nInfo,&_rValue,sizeof _rValue,&nValueLen),
     570           0 :         _aConnectionHandle,SQL_HANDLE_DBC,_xInterface);
     571           0 : }
     572             : // -------------------------------------------------------------------------
     573           0 : void OTools::GetInfo(OConnection* _pConnection,
     574             :                      SQLHANDLE _aConnectionHandle,
     575             :                      SQLUSMALLINT _nInfo,
     576             :                      sal_Bool &_rValue,
     577             :                      const Reference< XInterface >& _xInterface) throw(SQLException, RuntimeException)
     578             : {
     579             :     SQLSMALLINT nValueLen;
     580             :     OTools::ThrowException(_pConnection,
     581           0 :                             (*(T3SQLGetInfo)_pConnection->getOdbcFunction(ODBC3SQLGetInfo))(_aConnectionHandle,_nInfo,&_rValue,sizeof _rValue,&nValueLen),
     582           0 :                             _aConnectionHandle,SQL_HANDLE_DBC,_xInterface);
     583           0 : }
     584             : // -------------------------------------------------------------------------
     585           0 : sal_Int32 OTools::MapOdbcType2Jdbc(SQLSMALLINT _nType)
     586             : {
     587           0 :     sal_Int32 nValue = DataType::VARCHAR;
     588           0 :     switch(_nType)
     589             :     {
     590             :         case SQL_BIT:
     591           0 :             nValue = DataType::BIT;
     592           0 :             break;
     593             :         case SQL_TINYINT:
     594           0 :             nValue = DataType::TINYINT;
     595           0 :             break;
     596             :         case SQL_SMALLINT:
     597           0 :             nValue = DataType::SMALLINT;
     598           0 :             break;
     599             :         case SQL_INTEGER:
     600           0 :             nValue = DataType::INTEGER;
     601           0 :             break;
     602             :         case SQL_BIGINT:
     603           0 :             nValue = DataType::BIGINT;
     604           0 :             break;
     605             :         case SQL_FLOAT:
     606           0 :             nValue = DataType::FLOAT;
     607           0 :             break;
     608             :         case SQL_REAL:
     609           0 :             nValue = DataType::REAL;
     610           0 :             break;
     611             :         case SQL_DOUBLE:
     612           0 :             nValue = DataType::DOUBLE;
     613           0 :             break;
     614             :         case SQL_NUMERIC:
     615           0 :             nValue = DataType::NUMERIC;
     616           0 :             break;
     617             :         case SQL_DECIMAL:
     618           0 :             nValue = DataType::DECIMAL;
     619           0 :             break;
     620             :         case SQL_WCHAR:
     621             :         case SQL_CHAR:
     622           0 :             nValue = DataType::CHAR;
     623           0 :             break;
     624             :         case SQL_WVARCHAR:
     625             :         case SQL_VARCHAR:
     626           0 :             nValue = DataType::VARCHAR;
     627           0 :             break;
     628             :         case SQL_WLONGVARCHAR:
     629             :         case SQL_LONGVARCHAR:
     630           0 :             nValue = DataType::LONGVARCHAR;
     631           0 :             break;
     632             :         case SQL_TYPE_DATE:
     633             :         case SQL_DATE:
     634           0 :             nValue = DataType::DATE;
     635           0 :             break;
     636             :         case SQL_TYPE_TIME:
     637             :         case SQL_TIME:
     638           0 :             nValue = DataType::TIME;
     639           0 :             break;
     640             :         case SQL_TYPE_TIMESTAMP:
     641             :         case SQL_TIMESTAMP:
     642           0 :             nValue = DataType::TIMESTAMP;
     643           0 :             break;
     644             :         case SQL_BINARY:
     645           0 :             nValue = DataType::BINARY;
     646           0 :             break;
     647             :         case SQL_VARBINARY:
     648             :         case SQL_GUID:
     649           0 :             nValue = DataType::VARBINARY;
     650           0 :             break;
     651             :         case SQL_LONGVARBINARY:
     652           0 :             nValue = DataType::LONGVARBINARY;
     653           0 :             break;
     654             :         default:
     655             :             OSL_ASSERT(!"Invalid type");
     656             :     }
     657           0 :     return nValue;
     658             : }
     659             : //--------------------------------------------------------------------
     660             : // jdbcTypeToOdbc
     661             : // Convert the JDBC SQL type to the correct ODBC type
     662             : //--------------------------------------------------------------------
     663           0 : SQLSMALLINT OTools::jdbcTypeToOdbc(sal_Int32 jdbcType)
     664             : {
     665             :     RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "odbc", "Ocke.Janssen@sun.com", "OTools::jdbcTypeToOdbc" );
     666             :     // For the most part, JDBC types match ODBC types.  We'll
     667             :     // just convert the ones that we know are different
     668             : 
     669           0 :     sal_Int32 odbcType = jdbcType;
     670             : 
     671           0 :     switch (jdbcType)
     672             :     {
     673             :     case DataType::DATE:
     674           0 :         odbcType = SQL_DATE;
     675           0 :         break;
     676             :     case DataType::TIME:
     677           0 :         odbcType = SQL_TIME;
     678           0 :         break;
     679             :     case DataType::TIMESTAMP:
     680           0 :         odbcType = SQL_TIMESTAMP;
     681           0 :         break;
     682             :     // ODBC doesn't have any notion of CLOB or BLOB
     683             :     case DataType::CLOB:
     684           0 :         odbcType = SQL_LONGVARCHAR;
     685           0 :         break;
     686             :     case DataType::BLOB:
     687           0 :         odbcType = SQL_LONGVARBINARY;
     688           0 :         break;
     689             :     }
     690             : 
     691           0 :     return odbcType;
     692             : }
     693             : //-----------------------------------------------------------------------------
     694           0 : void OTools::getBindTypes(sal_Bool _bUseWChar,
     695             :                           sal_Bool _bUseOldTimeDate,
     696             :                           SQLSMALLINT _nOdbcType,
     697             :                           SQLSMALLINT& fCType,
     698             :                           SQLSMALLINT& fSqlType
     699             :                           )
     700             : {
     701             :     RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "odbc", "Ocke.Janssen@sun.com", "OTools::getBindTypes" );
     702           0 :     switch(_nOdbcType)
     703             :     {
     704           0 :         case SQL_CHAR:              if(_bUseWChar)
     705             :                                     {
     706           0 :                                         fCType   = SQL_C_WCHAR;
     707           0 :                                         fSqlType = SQL_WCHAR;
     708             :                                     }
     709             :                                     else
     710             :                                     {
     711           0 :                                         fCType   = SQL_C_CHAR;
     712           0 :                                         fSqlType = SQL_CHAR;
     713             :                                     }
     714           0 :                                     break;
     715           0 :         case SQL_VARCHAR:           if(_bUseWChar)
     716             :                                     {
     717           0 :                                         fCType   = SQL_C_WCHAR;
     718           0 :                                         fSqlType = SQL_WVARCHAR;
     719             :                                     }
     720             :                                     else
     721             :                                     {
     722           0 :                                         fCType   = SQL_C_CHAR;
     723           0 :                                         fSqlType = SQL_VARCHAR;
     724             :                                     }
     725           0 :                                     break;
     726           0 :         case SQL_LONGVARCHAR:       if(_bUseWChar)
     727             :                                     {
     728           0 :                                         fCType   = SQL_C_WCHAR;
     729           0 :                                         fSqlType = SQL_WLONGVARCHAR;
     730             :                                     }
     731             :                                     else
     732             :                                     {
     733           0 :                                         fCType   = SQL_C_CHAR;
     734           0 :                                         fSqlType = SQL_LONGVARCHAR;
     735             :                                     }
     736           0 :                                     break;
     737           0 :         case SQL_DECIMAL:           fCType      = _bUseWChar ? SQL_C_WCHAR : SQL_C_CHAR;
     738           0 :                                     fSqlType    = SQL_DECIMAL; break;
     739           0 :         case SQL_NUMERIC:           fCType      = _bUseWChar ? SQL_C_WCHAR : SQL_C_CHAR;
     740           0 :                                     fSqlType    = SQL_NUMERIC; break;
     741           0 :         case SQL_BIT:               fCType      = SQL_C_TINYINT;
     742           0 :                                     fSqlType    = SQL_INTEGER; break;
     743           0 :         case SQL_TINYINT:           fCType      = SQL_C_TINYINT;
     744           0 :                                     fSqlType    = SQL_TINYINT; break;
     745           0 :         case SQL_SMALLINT:          fCType      = SQL_C_SHORT;
     746           0 :                                     fSqlType    = SQL_SMALLINT; break;
     747           0 :         case SQL_INTEGER:           fCType      = SQL_C_LONG;
     748           0 :                                     fSqlType    = SQL_INTEGER; break;
     749           0 :         case SQL_BIGINT:            fCType      = SQL_C_SBIGINT;
     750           0 :                                     fSqlType    = SQL_BIGINT; break;
     751           0 :         case SQL_FLOAT:             fCType      = SQL_C_FLOAT;
     752           0 :                                     fSqlType    = SQL_FLOAT; break;
     753           0 :         case SQL_REAL:              fCType      = SQL_C_DOUBLE;
     754           0 :                                     fSqlType    = SQL_REAL; break;
     755           0 :         case SQL_DOUBLE:            fCType      = SQL_C_DOUBLE;
     756           0 :                                     fSqlType    = SQL_DOUBLE; break;
     757           0 :         case SQL_BINARY:            fCType      = SQL_C_BINARY;
     758           0 :                                     fSqlType    = SQL_BINARY; break;
     759             :         case SQL_VARBINARY:
     760           0 :                                     fCType      = SQL_C_BINARY;
     761           0 :                                     fSqlType    = SQL_VARBINARY; break;
     762           0 :         case SQL_LONGVARBINARY:     fCType      = SQL_C_BINARY;
     763           0 :                                     fSqlType    = SQL_LONGVARBINARY; break;
     764             :         case SQL_DATE:
     765           0 :                                     if(_bUseOldTimeDate)
     766             :                                     {
     767           0 :                                         fCType      = SQL_C_DATE;
     768           0 :                                         fSqlType    = SQL_DATE;
     769             :                                     }
     770             :                                     else
     771             :                                     {
     772           0 :                                         fCType      = SQL_C_TYPE_DATE;
     773           0 :                                         fSqlType    = SQL_TYPE_DATE;
     774             :                                     }
     775           0 :                                     break;
     776             :         case SQL_TIME:
     777           0 :                                     if(_bUseOldTimeDate)
     778             :                                     {
     779           0 :                                         fCType      = SQL_C_TIME;
     780           0 :                                         fSqlType    = SQL_TIME;
     781             :                                     }
     782             :                                     else
     783             :                                     {
     784           0 :                                         fCType      = SQL_C_TYPE_TIME;
     785           0 :                                         fSqlType    = SQL_TYPE_TIME;
     786             :                                     }
     787           0 :                                     break;
     788             :         case SQL_TIMESTAMP:
     789           0 :                                     if(_bUseOldTimeDate)
     790             :                                     {
     791           0 :                                         fCType      = SQL_C_TIMESTAMP;
     792           0 :                                         fSqlType    = SQL_TIMESTAMP;
     793             :                                     }
     794             :                                     else
     795             :                                     {
     796           0 :                                         fCType      = SQL_C_TYPE_TIMESTAMP;
     797           0 :                                         fSqlType    = SQL_TYPE_TIMESTAMP;
     798             :                                     }
     799           0 :                                     break;
     800           0 :         default:                        fCType      = SQL_C_BINARY;
     801           0 :                                         fSqlType    = SQL_LONGVARBINARY; break;
     802             :     }
     803           0 : }
     804             : 
     805             : 
     806             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10