1 /**************************************************************
2 *
3 * Licensed to the Apache Software Foundation (ASF) under one
4 * or more contributor license agreements. See the NOTICE file
5 * distributed with this work for additional information
6 * regarding copyright ownership. The ASF licenses this file
7 * to you under the Apache License, Version 2.0 (the
8 * "License"); you may not use this file except in compliance
9 * with the License. You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing,
14 * software distributed under the License is distributed on an
15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16 * KIND, either express or implied. See the License for the
17 * specific language governing permissions and limitations
18 * under the License.
19 *
20 *************************************************************/
21
22
23
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_connectivity.hxx"
26 #include "ado/AConnection.hxx"
27 #include "ado/ADatabaseMetaData.hxx"
28 #include "ado/ADriver.hxx"
29 #include "ado/AStatement.hxx"
30 #include "ado/ACallableStatement.hxx"
31 #include "ado/APreparedStatement.hxx"
32 #include "ado/ACatalog.hxx"
33 #include <com/sun/star/sdbc/ColumnValue.hpp>
34 #include <com/sun/star/sdbc/TransactionIsolation.hpp>
35 #include <com/sun/star/sdbc/XRow.hpp>
36 #include <com/sun/star/lang/DisposedException.hpp>
37 #include <cppuhelper/typeprovider.hxx>
38 #include "connectivity/dbexception.hxx"
39 #include <osl/file.hxx>
40 #include "resource/ado_res.hrc"
41
42 using namespace dbtools;
43 using namespace connectivity::ado;
44 using namespace com::sun::star::uno;
45 using namespace com::sun::star::lang;
46 using namespace com::sun::star::beans;
47 using namespace com::sun::star::sdbc;
48 using namespace com::sun::star::sdbcx;
49
50 //------------------------------------------------------------------------------
51 IMPLEMENT_SERVICE_INFO(OConnection,"com.sun.star.sdbcx.AConnection","com.sun.star.sdbc.Connection");
52 // --------------------------------------------------------------------------------
OConnection(ODriver * _pDriver)53 OConnection::OConnection(ODriver* _pDriver) throw(SQLException, RuntimeException)
54 : OSubComponent<OConnection, OConnection_BASE>((::cppu::OWeakObject*)_pDriver, this),
55 m_bClosed(sal_False),
56 m_xCatalog(NULL),
57 m_pDriver(_pDriver),
58 m_pAdoConnection(NULL),
59 m_bAutocommit(sal_True),
60 m_nEngineType(0),
61 m_pCatalog(NULL)
62 {
63 osl_incrementInterlockedCount( &m_refCount );
64
65 IClassFactory2* pIUnknown = NULL;
66 IUnknown *pOuter = NULL;
67 HRESULT hr;
68 hr = CoGetClassObject( ADOS::CLSID_ADOCONNECTION_21,
69 CLSCTX_INPROC_SERVER,
70 NULL,
71 IID_IClassFactory2,
72 (void**)&pIUnknown );
73
74 if( !FAILED( hr ) )
75 {
76 ADOConnection *pCon = NULL;
77 hr = pIUnknown->CreateInstanceLic( pOuter,
78 NULL,
79 ADOS::IID_ADOCONNECTION_21,
80 ADOS::GetKeyStr(),
81 (void**) &pCon);
82
83 if( !FAILED( hr ) )
84 {
85 OSL_ENSURE( pCon, "OConnection::OConnection: invalid ADO object!" );
86
87 m_pAdoConnection = new WpADOConnection( pCon );
88 // CreateInstanceLic returned an object which was already acquired
89 pCon->Release( );
90
91 }
92
93 // Class Factory is no longer needed
94 pIUnknown->Release();
95 }
96
97 osl_decrementInterlockedCount( &m_refCount );
98 }
99 //-----------------------------------------------------------------------------
~OConnection()100 OConnection::~OConnection()
101 {
102 }
103 //-----------------------------------------------------------------------------
construct(const::rtl::OUString & url,const Sequence<PropertyValue> & info)104 void OConnection::construct(const ::rtl::OUString& url,const Sequence< PropertyValue >& info)
105 {
106 osl_incrementInterlockedCount( &m_refCount );
107
108 setConnectionInfo(info);
109
110 sal_Int32 nLen = url.indexOf(':');
111 nLen = url.indexOf(':',nLen+1);
112 ::rtl::OUString aDSN(url.copy(nLen+1)),aUID,aPWD;
113 if ( aDSN.compareToAscii("access:",7) == 0 )
114 aDSN = aDSN.copy(7);
115
116 sal_Int32 nTimeout = 20;
117 sal_Bool bSilent = sal_True;
118 const PropertyValue *pIter = info.getConstArray();
119 const PropertyValue *pEnd = pIter + info.getLength();
120 for(;pIter != pEnd;++pIter)
121 {
122 if(!pIter->Name.compareToAscii("Timeout"))
123 pIter->Value >>= nTimeout;
124 else if(!pIter->Name.compareToAscii("Silent"))
125 pIter->Value >>= bSilent;
126 else if(!pIter->Name.compareToAscii("user"))
127 pIter->Value >>= aUID;
128 else if(!pIter->Name.compareToAscii("password"))
129 pIter->Value >>= aPWD;
130 }
131 try
132 {
133 if(m_pAdoConnection)
134 {
135 if(m_pAdoConnection->Open(aDSN,aUID,aPWD,adConnectUnspecified))
136 m_pAdoConnection->PutCommandTimeout(nTimeout);
137 else
138 ADOS::ThrowException(*m_pAdoConnection,*this);
139 if(m_pAdoConnection->get_State() != adStateOpen)
140 throwGenericSQLException( STR_NO_CONNECTION,*this );
141
142 WpADOProperties aProps = m_pAdoConnection->get_Properties();
143 if(aProps.IsValid())
144 {
145 OTools::putValue(aProps,::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Jet OLEDB:ODBC Parsing")),sal_True);
146 OLEVariant aVar(OTools::getValue(aProps,::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Jet OLEDB:Engine Type"))));
147 if(!aVar.isNull() && !aVar.isEmpty())
148 m_nEngineType = aVar;
149 }
150 buildTypeInfo();
151 //bErg = TRUE;
152 }
153 else
154 ::dbtools::throwFunctionSequenceException(*this);
155
156 }
157 catch(const Exception )
158 {
159 osl_decrementInterlockedCount( &m_refCount );
160 throw;
161 }
162 osl_decrementInterlockedCount( &m_refCount );
163 }
164 //-----------------------------------------------------------------------------
release()165 void SAL_CALL OConnection::release() throw()
166 {
167 relase_ChildImpl();
168 }
169 // --------------------------------------------------------------------------------
createStatement()170 Reference< XStatement > SAL_CALL OConnection::createStatement( ) throw(SQLException, RuntimeException)
171 {
172 ::osl::MutexGuard aGuard( m_aMutex );
173 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
174
175 OStatement* pStmt = new OStatement(this);
176 Reference< XStatement > xStmt = pStmt;
177 m_aStatements.push_back(WeakReferenceHelper(*pStmt));
178 return pStmt;
179 }
180 // --------------------------------------------------------------------------------
prepareStatement(const::rtl::OUString & sql)181 Reference< XPreparedStatement > SAL_CALL OConnection::prepareStatement( const ::rtl::OUString& sql ) throw(SQLException, RuntimeException)
182 {
183 ::osl::MutexGuard aGuard( m_aMutex );
184 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
185
186
187 OPreparedStatement* pStmt = new OPreparedStatement(this,m_aTypeInfo,sql);
188 Reference< XPreparedStatement > xPStmt = pStmt;
189 m_aStatements.push_back(WeakReferenceHelper(*pStmt));
190 return xPStmt;
191 }
192 // --------------------------------------------------------------------------------
prepareCall(const::rtl::OUString & sql)193 Reference< XPreparedStatement > SAL_CALL OConnection::prepareCall( const ::rtl::OUString& sql ) throw(SQLException, RuntimeException)
194 {
195 ::osl::MutexGuard aGuard( m_aMutex );
196 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
197
198
199 OCallableStatement* pStmt = new OCallableStatement(this,m_aTypeInfo,sql);
200 Reference< XPreparedStatement > xPStmt = pStmt;
201 m_aStatements.push_back(WeakReferenceHelper(*pStmt));
202 return xPStmt;
203 }
204 // --------------------------------------------------------------------------------
nativeSQL(const::rtl::OUString & _sql)205 ::rtl::OUString SAL_CALL OConnection::nativeSQL( const ::rtl::OUString& _sql ) throw(SQLException, RuntimeException)
206 {
207 ::osl::MutexGuard aGuard( m_aMutex );
208 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
209
210
211 ::rtl::OUString sql = _sql;
212 WpADOProperties aProps = m_pAdoConnection->get_Properties();
213 if(aProps.IsValid())
214 {
215 OTools::putValue(aProps,::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Jet OLEDB:ODBC Parsing")),sal_True);
216 WpADOCommand aCommand;
217 aCommand.Create();
218 aCommand.put_ActiveConnection((IDispatch*)*m_pAdoConnection);
219 aCommand.put_CommandText(sql);
220 sql = aCommand.get_CommandText();
221 }
222
223 return sql;
224 }
225 // --------------------------------------------------------------------------------
setAutoCommit(sal_Bool autoCommit)226 void SAL_CALL OConnection::setAutoCommit( sal_Bool autoCommit ) throw(SQLException, RuntimeException)
227 {
228 ::osl::MutexGuard aGuard( m_aMutex );
229 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
230
231
232 m_bAutocommit = autoCommit;
233 if(!autoCommit)
234 m_pAdoConnection->BeginTrans();
235 else
236 m_pAdoConnection->RollbackTrans();
237 }
238 // --------------------------------------------------------------------------------
getAutoCommit()239 sal_Bool SAL_CALL OConnection::getAutoCommit( ) throw(SQLException, RuntimeException)
240 {
241 ::osl::MutexGuard aGuard( m_aMutex );
242 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
243
244
245 return m_bAutocommit;
246 }
247 // --------------------------------------------------------------------------------
commit()248 void SAL_CALL OConnection::commit( ) throw(SQLException, RuntimeException)
249 {
250 ::osl::MutexGuard aGuard( m_aMutex );
251 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
252
253
254 m_pAdoConnection->CommitTrans();
255 }
256 // --------------------------------------------------------------------------------
rollback()257 void SAL_CALL OConnection::rollback( ) throw(SQLException, RuntimeException)
258 {
259 ::osl::MutexGuard aGuard( m_aMutex );
260 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
261
262
263 m_pAdoConnection->RollbackTrans();
264 }
265 // --------------------------------------------------------------------------------
isClosed()266 sal_Bool SAL_CALL OConnection::isClosed( ) throw(SQLException, RuntimeException)
267 {
268 ::osl::MutexGuard aGuard( m_aMutex );
269
270 return OConnection_BASE::rBHelper.bDisposed && !m_pAdoConnection->get_State();
271 }
272 // --------------------------------------------------------------------------------
getMetaData()273 Reference< XDatabaseMetaData > SAL_CALL OConnection::getMetaData( ) throw(SQLException, RuntimeException)
274 {
275 ::osl::MutexGuard aGuard( m_aMutex );
276 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
277
278
279 Reference< XDatabaseMetaData > xMetaData = m_xMetaData;
280 if(!xMetaData.is())
281 {
282 xMetaData = new ODatabaseMetaData(this);
283 m_xMetaData = xMetaData;
284 }
285
286 return xMetaData;
287 }
288 // --------------------------------------------------------------------------------
setReadOnly(sal_Bool readOnly)289 void SAL_CALL OConnection::setReadOnly( sal_Bool readOnly ) throw(SQLException, RuntimeException)
290 {
291 ::osl::MutexGuard aGuard( m_aMutex );
292 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
293
294
295
296 m_pAdoConnection->put_Mode(readOnly ? adModeRead : adModeReadWrite);
297 ADOS::ThrowException(*m_pAdoConnection,*this);
298 }
299 // --------------------------------------------------------------------------------
isReadOnly()300 sal_Bool SAL_CALL OConnection::isReadOnly( ) throw(SQLException, RuntimeException)
301 {
302 ::osl::MutexGuard aGuard( m_aMutex );
303 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
304
305
306 return m_pAdoConnection->get_Mode() == adModeRead;
307 }
308 // --------------------------------------------------------------------------------
setCatalog(const::rtl::OUString & catalog)309 void SAL_CALL OConnection::setCatalog( const ::rtl::OUString& catalog ) throw(SQLException, RuntimeException)
310 {
311 ::osl::MutexGuard aGuard( m_aMutex );
312 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
313
314 m_pAdoConnection->PutDefaultDatabase(catalog);
315 ADOS::ThrowException(*m_pAdoConnection,*this);
316 }
317 // --------------------------------------------------------------------------------
getCatalog()318 ::rtl::OUString SAL_CALL OConnection::getCatalog( ) throw(SQLException, RuntimeException)
319 {
320 ::osl::MutexGuard aGuard( m_aMutex );
321 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
322
323 return m_pAdoConnection->GetDefaultDatabase();
324 }
325 // --------------------------------------------------------------------------------
setTransactionIsolation(sal_Int32 level)326 void SAL_CALL OConnection::setTransactionIsolation( sal_Int32 level ) throw(SQLException, RuntimeException)
327 {
328 ::osl::MutexGuard aGuard( m_aMutex );
329 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
330
331
332 IsolationLevelEnum eIso;
333 switch(level)
334 {
335 case TransactionIsolation::NONE:
336 eIso = adXactUnspecified;
337 break;
338 case TransactionIsolation::READ_UNCOMMITTED:
339 eIso = adXactReadUncommitted;
340 break;
341 case TransactionIsolation::READ_COMMITTED:
342 eIso = adXactReadCommitted;
343 break;
344 case TransactionIsolation::REPEATABLE_READ:
345 eIso = adXactRepeatableRead;
346 break;
347 case TransactionIsolation::SERIALIZABLE:
348 eIso = adXactSerializable;
349 break;
350 default:
351 OSL_ENSURE(0,"OConnection::setTransactionIsolation invalid level");
352 return;
353 }
354 m_pAdoConnection->put_IsolationLevel(eIso);
355 ADOS::ThrowException(*m_pAdoConnection,*this);
356 }
357 // --------------------------------------------------------------------------------
getTransactionIsolation()358 sal_Int32 SAL_CALL OConnection::getTransactionIsolation( ) throw(SQLException, RuntimeException)
359 {
360 ::osl::MutexGuard aGuard( m_aMutex );
361 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
362
363
364 sal_Int32 nRet = 0;
365 switch(m_pAdoConnection->get_IsolationLevel())
366 {
367 case adXactUnspecified:
368 nRet = TransactionIsolation::NONE;
369 break;
370 case adXactReadUncommitted:
371 nRet = TransactionIsolation::READ_UNCOMMITTED;
372 break;
373 case adXactReadCommitted:
374 nRet = TransactionIsolation::READ_COMMITTED;
375 break;
376 case adXactRepeatableRead:
377 nRet = TransactionIsolation::REPEATABLE_READ;
378 break;
379 case adXactSerializable:
380 nRet = TransactionIsolation::SERIALIZABLE;
381 break;
382 default:
383 OSL_ENSURE(0,"OConnection::setTransactionIsolation invalid level");
384 }
385 ADOS::ThrowException(*m_pAdoConnection,*this);
386 return nRet;
387 }
388 // --------------------------------------------------------------------------------
getTypeMap()389 Reference< ::com::sun::star::container::XNameAccess > SAL_CALL OConnection::getTypeMap( ) throw(SQLException, RuntimeException)
390 {
391 ::osl::MutexGuard aGuard( m_aMutex );
392 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
393
394
395 return NULL;
396 }
397 // --------------------------------------------------------------------------------
setTypeMap(const Reference<::com::sun::star::container::XNameAccess> &)398 void SAL_CALL OConnection::setTypeMap( const Reference< ::com::sun::star::container::XNameAccess >& /*typeMap*/ ) throw(SQLException, RuntimeException)
399 {
400 ::dbtools::throwFeatureNotImplementedException( "XConnection::setTypeMap", *this );
401 }
402 // --------------------------------------------------------------------------------
403 // XCloseable
close()404 void SAL_CALL OConnection::close( ) throw(SQLException, RuntimeException)
405 {
406 {
407 ::osl::MutexGuard aGuard( m_aMutex );
408 checkDisposed(OConnection_BASE::rBHelper.bDisposed);
409
410 }
411 dispose();
412 }
413 // --------------------------------------------------------------------------------
414 // XWarningsSupplier
getWarnings()415 Any SAL_CALL OConnection::getWarnings( ) throw(SQLException, RuntimeException)
416 {
417 return Any();
418 }
419 // --------------------------------------------------------------------------------
clearWarnings()420 void SAL_CALL OConnection::clearWarnings( ) throw(SQLException, RuntimeException)
421 {
422 }
423 //--------------------------------------------------------------------
buildTypeInfo()424 void OConnection::buildTypeInfo() throw( SQLException)
425 {
426 ::osl::MutexGuard aGuard( m_aMutex );
427
428 ADORecordset *pRecordset = m_pAdoConnection->getTypeInfo();
429 if ( pRecordset )
430 {
431 pRecordset->AddRef();
432 VARIANT_BOOL bIsAtBOF;
433 pRecordset->get_BOF(&bIsAtBOF);
434
435 sal_Bool bOk = sal_True;
436 if ( bIsAtBOF == VARIANT_TRUE )
437 bOk = SUCCEEDED(pRecordset->MoveNext());
438
439 if ( bOk )
440 {
441 // HACK for access
442 static const ::rtl::OUString s_sVarChar(RTL_CONSTASCII_USTRINGPARAM("VarChar"));
443 do
444 {
445 sal_Int32 nPos = 1;
446 OExtendedTypeInfo* aInfo = new OExtendedTypeInfo();
447 aInfo->aSimpleType.aTypeName = ADOS::getField(pRecordset,nPos++).get_Value();
448 aInfo->eType = (DataTypeEnum)(sal_Int32)ADOS::getField(pRecordset,nPos++).get_Value();
449 if ( aInfo->eType == adWChar && aInfo->aSimpleType.aTypeName == s_sVarChar )
450 aInfo->eType = adVarWChar;
451 aInfo->aSimpleType.nType = (sal_Int16)ADOS::MapADOType2Jdbc(static_cast<DataTypeEnum>(aInfo->eType));
452 aInfo->aSimpleType.nPrecision = ADOS::getField(pRecordset,nPos++).get_Value();
453 aInfo->aSimpleType.aLiteralPrefix = ADOS::getField(pRecordset,nPos++).get_Value();
454 aInfo->aSimpleType.aLiteralSuffix = ADOS::getField(pRecordset,nPos++).get_Value();
455 aInfo->aSimpleType.aCreateParams = ADOS::getField(pRecordset,nPos++).get_Value();
456 aInfo->aSimpleType.bNullable = ADOS::getField(pRecordset,nPos++).get_Value();
457 aInfo->aSimpleType.bCaseSensitive = ADOS::getField(pRecordset,nPos++).get_Value();
458 aInfo->aSimpleType.nSearchType = ADOS::getField(pRecordset,nPos++).get_Value();
459 aInfo->aSimpleType.bUnsigned = ADOS::getField(pRecordset,nPos++).get_Value();
460 aInfo->aSimpleType.bCurrency = ADOS::getField(pRecordset,nPos++).get_Value();
461 aInfo->aSimpleType.bAutoIncrement = ADOS::getField(pRecordset,nPos++).get_Value();
462 aInfo->aSimpleType.aLocalTypeName = ADOS::getField(pRecordset,nPos++).get_Value();
463 aInfo->aSimpleType.nMinimumScale = ADOS::getField(pRecordset,nPos++).get_Value();
464 aInfo->aSimpleType.nMaximumScale = ADOS::getField(pRecordset,nPos++).get_Value();
465 if ( adCurrency == aInfo->eType && !aInfo->aSimpleType.nMaximumScale)
466 {
467 aInfo->aSimpleType.nMinimumScale = 4;
468 aInfo->aSimpleType.nMaximumScale = 4;
469 }
470 aInfo->aSimpleType.nNumPrecRadix = ADOS::getField(pRecordset,nPos++).get_Value();
471 // Now that we have the type info, save it
472 // in the Hashtable if we don't already have an
473 // entry for this SQL type.
474
475 m_aTypeInfo.insert(OTypeInfoMap::value_type(aInfo->eType,aInfo));
476 }
477 while ( SUCCEEDED(pRecordset->MoveNext()) );
478 }
479 pRecordset->Release();
480 }
481 }
482 //------------------------------------------------------------------------------
disposing()483 void OConnection::disposing()
484 {
485 ::osl::MutexGuard aGuard(m_aMutex);
486
487 OConnection_BASE::disposing();
488
489 m_bClosed = sal_True;
490 m_xMetaData = ::com::sun::star::uno::WeakReference< ::com::sun::star::sdbc::XDatabaseMetaData>();
491 m_xCatalog = ::com::sun::star::uno::WeakReference< ::com::sun::star::sdbcx::XTablesSupplier>();
492 m_pDriver = NULL;
493
494 m_pAdoConnection->Close();
495
496 OTypeInfoMap::iterator aIter = m_aTypeInfo.begin();
497 for (; aIter != m_aTypeInfo.end(); ++aIter)
498 delete aIter->second;
499
500 m_aTypeInfo.clear();
501
502 delete m_pAdoConnection;
503 m_pAdoConnection = NULL;
504
505 dispose_ChildImpl();
506 }
507 // -----------------------------------------------------------------------------
getSomething(const::com::sun::star::uno::Sequence<sal_Int8> & rId)508 sal_Int64 SAL_CALL OConnection::getSomething( const ::com::sun::star::uno::Sequence< sal_Int8 >& rId ) throw (::com::sun::star::uno::RuntimeException)
509 {
510 return (rId.getLength() == 16 && 0 == rtl_compareMemory(getUnoTunnelImplementationId().getConstArray(), rId.getConstArray(), 16 ) )
511 ?
512 reinterpret_cast< sal_Int64 >( this )
513 :
514 OConnection_BASE::getSomething(rId);
515 }
516 // -----------------------------------------------------------------------------
getUnoTunnelImplementationId()517 Sequence< sal_Int8 > OConnection::getUnoTunnelImplementationId()
518 {
519 static ::cppu::OImplementationId * pId = 0;
520 if (! pId)
521 {
522 ::osl::MutexGuard aGuard( ::osl::Mutex::getGlobalMutex() );
523 if (! pId)
524 {
525 static ::cppu::OImplementationId aId;
526 pId = &aId;
527 }
528 }
529 return pId->getImplementationId();
530 }
531 // -----------------------------------------------------------------------------
getTypeInfoFromType(const OTypeInfoMap & _rTypeInfo,DataTypeEnum _nType,const::rtl::OUString & _sTypeName,sal_Int32 _nPrecision,sal_Int32 _nScale,sal_Bool & _brForceToType)532 const OExtendedTypeInfo* OConnection::getTypeInfoFromType(const OTypeInfoMap& _rTypeInfo,
533 DataTypeEnum _nType,
534 const ::rtl::OUString& _sTypeName,
535 sal_Int32 _nPrecision,
536 sal_Int32 _nScale,
537 sal_Bool& _brForceToType)
538 {
539 const OExtendedTypeInfo* pTypeInfo = NULL;
540 _brForceToType = sal_False;
541 // search for type
542 ::std::pair<OTypeInfoMap::const_iterator, OTypeInfoMap::const_iterator> aPair = _rTypeInfo.equal_range(_nType);
543 OTypeInfoMap::const_iterator aIter = aPair.first;
544 if(aIter != _rTypeInfo.end()) // compare with end is correct here
545 {
546 for(;aIter != aPair.second;++aIter)
547 {
548 // search the best matching type
549 OExtendedTypeInfo* pInfo = aIter->second;
550 #ifdef DBG_UTIL
551 ::rtl::OUString sDBTypeName = pInfo->aSimpleType.aTypeName;
552 sal_Int32 nDBTypePrecision = pInfo->aSimpleType.nPrecision; (void)nDBTypePrecision;
553 sal_Int32 nDBTypeScale = pInfo->aSimpleType.nMaximumScale; (void)nDBTypeScale;
554 sal_Int32 nAdoType = pInfo->eType; (void)nAdoType;
555 #endif
556 if ( ( !_sTypeName.getLength()
557 || (pInfo->aSimpleType.aTypeName.equalsIgnoreAsciiCase(_sTypeName))
558 )
559 && (pInfo->aSimpleType.nPrecision >= _nPrecision)
560 && (pInfo->aSimpleType.nMaximumScale >= _nScale)
561
562 )
563 break;
564 }
565
566 if (aIter == aPair.second)
567 {
568 for(aIter = aPair.first; aIter != aPair.second; ++aIter)
569 {
570 // search the best matching type (now comparing the local names)
571 if ( (aIter->second->aSimpleType.aLocalTypeName.equalsIgnoreAsciiCase(_sTypeName))
572 && (aIter->second->aSimpleType.nPrecision >= _nPrecision)
573 && (aIter->second->aSimpleType.nMaximumScale >= _nScale)
574 )
575 {
576 // we can not assert here because we could be in d&d
577 /*
578 OSL_ENSURE(sal_False,
579 ( ::rtl::OString("getTypeInfoFromType: assuming column type ")
580 += ::rtl::OString(aIter->second->aTypeName.getStr(), aIter->second->aTypeName.getLength(), gsl_getSystemTextEncoding())
581 += ::rtl::OString("\" (expected type name ")
582 += ::rtl::OString(_sTypeName.getStr(), _sTypeName.getLength(), gsl_getSystemTextEncoding())
583 += ::rtl::OString(" matches the type's local name).")).getStr());
584 */
585 break;
586 }
587 }
588 }
589
590 if (aIter == aPair.second)
591 { // no match for the names, no match for the local names
592 // -> drop the precision and the scale restriction, accept any type with the property
593 // type id (nType)
594
595 // we can not assert here because we could be in d&d
596 pTypeInfo = aPair.first->second;
597 _brForceToType = sal_True;
598 }
599 else
600 pTypeInfo = aIter->second;
601 }
602 else if ( _sTypeName.getLength() )
603 {
604 ::comphelper::TStringMixEqualFunctor aCase(sal_False);
605 // search for typeinfo where the typename is equal _sTypeName
606 OTypeInfoMap::const_iterator aFind = ::std::find_if(_rTypeInfo.begin(),
607 _rTypeInfo.end(),
608 ::std::compose1(
609 ::std::bind2nd(aCase, _sTypeName),
610 ::std::compose1(
611 ::std::mem_fun(&OExtendedTypeInfo::getDBName),
612 ::std::select2nd<OTypeInfoMap::value_type>())
613 )
614 );
615 if(aFind != _rTypeInfo.end())
616 pTypeInfo = aFind->second;
617 }
618
619 // we can not assert here because we could be in d&d
620 // OSL_ENSURE(pTypeInfo, "getTypeInfoFromType: no type info found for this type!");
621 return pTypeInfo;
622 }
623 // -----------------------------------------------------------------------------
624
625
626
627