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 27 28 #include <connectivity/sqlnode.hxx> 29 #include <connectivity/sqlerror.hxx> 30 #include <internalnode.hxx> 31 #define YYBISON 1 32 #ifndef BISON_INCLUDED 33 #define BISON_INCLUDED 34 #include <sqlbison.hxx> 35 #endif 36 #include <connectivity/sqlparse.hxx> 37 #include <com/sun/star/lang/Locale.hpp> 38 #include <com/sun/star/util/XNumberFormatter.hpp> 39 #include <com/sun/star/util/XNumberFormatTypes.hpp> 40 #include <com/sun/star/i18n/NumberFormatIndex.hpp> 41 #include <com/sun/star/beans/XPropertySet.hpp> 42 #include <com/sun/star/sdbc/XDatabaseMetaData.hpp> 43 #include <com/sun/star/sdbc/DataType.hpp> 44 #include <com/sun/star/sdb/XQueriesSupplier.hpp> 45 #include <com/sun/star/sdb/ErrorCondition.hpp> 46 #include <com/sun/star/util/XNumberFormatter.hpp> 47 #include <com/sun/star/util/XNumberFormatsSupplier.hpp> 48 #include <com/sun/star/util/XNumberFormats.hpp> 49 #include <com/sun/star/util/NumberFormat.hpp> 50 #include <com/sun/star/util/XNumberFormatTypes.hpp> 51 #include <com/sun/star/lang/Locale.hpp> 52 #include <com/sun/star/i18n/KParseType.hpp> 53 #include <com/sun/star/i18n/KParseTokens.hpp> 54 #include "connectivity/dbconversion.hxx" 55 #include <com/sun/star/util/DateTime.hpp> 56 #include <com/sun/star/util/Time.hpp> 57 #include <com/sun/star/util/Date.hpp> 58 #include "TConnection.hxx" 59 #include "sqlscan.hxx" 60 #include <comphelper/numbers.hxx> 61 #include <comphelper/processfactory.hxx> 62 #include <comphelper/stl_types.hxx> 63 #include "connectivity/dbtools.hxx" 64 #include "connectivity/dbmetadata.hxx" 65 #include "connectivity/sqlerror.hxx" 66 #include <tools/diagnose_ex.h> 67 #include <string.h> 68 #include <boost/bind.hpp> 69 #include <algorithm> 70 #include <functional> 71 #include <rtl/logfile.hxx> 72 #include <rtl/ustrbuf.hxx> 73 74 using namespace ::com::sun::star::sdbc; 75 using namespace ::com::sun::star::util; 76 using namespace ::com::sun::star::beans; 77 using namespace ::com::sun::star::sdb; 78 using namespace ::com::sun::star::uno; 79 using namespace ::com::sun::star::lang; 80 using namespace ::com::sun::star::i18n; 81 using namespace ::com::sun::star; 82 using namespace ::osl; 83 using namespace ::dbtools; 84 using namespace ::comphelper; 85 86 87 extern int SQLyyparse (void); 88 extern ::rtl::OUString ConvertLikeToken(const ::connectivity::OSQLParseNode* pTokenNode, const ::connectivity::OSQLParseNode* pEscapeNode, sal_Bool bInternational); 89 extern void setParser( ::connectivity::OSQLParser* ); 90 91 namespace 92 { 93 // ----------------------------------------------------------------------------- 94 sal_Bool lcl_saveConvertToNumber(const Reference< XNumberFormatter > & _xFormatter,sal_Int32 _nKey,const ::rtl::OUString& _sValue,double& _nrValue) 95 { 96 sal_Bool bRet = sal_False; 97 try 98 { 99 _nrValue = _xFormatter->convertStringToNumber(_nKey, _sValue); 100 bRet = sal_True; 101 } 102 catch(Exception&) 103 { 104 } 105 return bRet; 106 } 107 // ----------------------------------------------------------------------------- 108 void replaceAndReset(connectivity::OSQLParseNode*& _pResetNode,connectivity::OSQLParseNode* _pNewNode) 109 { 110 _pResetNode->getParent()->replace(_pResetNode, _pNewNode); 111 delete _pResetNode; 112 _pResetNode = _pNewNode; 113 } 114 // ----------------------------------------------------------------------------- 115 /** quotes a string and search for quotes inside the string and replace them with the new quote 116 @param rValue 117 The value to be quoted. 118 @param rQuot 119 The quote 120 @param rQuotToReplace 121 The quote to replace with 122 @return 123 The quoted string. 124 */ 125 ::rtl::OUString SetQuotation(const ::rtl::OUString& rValue, const ::rtl::OUString& rQuot, const ::rtl::OUString& rQuotToReplace) 126 { 127 ::rtl::OUString rNewValue = rQuot; 128 rNewValue += rValue; 129 sal_Int32 nIndex = (sal_Int32)-1; // Quotes durch zweifache Quotes ersetzen, sonst kriegt der Parser Probleme 130 131 if (rQuot.getLength()) 132 { 133 do 134 { 135 nIndex += 2; 136 nIndex = rNewValue.indexOf(rQuot,nIndex); 137 if(nIndex != -1) 138 rNewValue = rNewValue.replaceAt(nIndex,rQuot.getLength(),rQuotToReplace); 139 } while (nIndex != -1); 140 } 141 142 rNewValue += rQuot; 143 return rNewValue; 144 } 145 } 146 147 namespace connectivity 148 { 149 150 //============================================================================= 151 //= OSQLParser_Data 152 //============================================================================= 153 //----------------------------------------------------------------------------- 154 OSQLParser_Data::OSQLParser_Data( const Reference< XMultiServiceFactory >& _xServiceFactory ) 155 :aErrors( _xServiceFactory ) 156 { 157 } 158 159 //============================================================================= 160 //= SQLParseNodeParameter 161 //============================================================================= 162 //----------------------------------------------------------------------------- 163 SQLParseNodeParameter::SQLParseNodeParameter( const Reference< XConnection >& _rxConnection, 164 const Reference< XNumberFormatter >& _xFormatter, const Reference< XPropertySet >& _xField, 165 const Locale& _rLocale, const IParseContext* _pContext, 166 bool _bIntl, bool _bQuote, sal_Char _cDecSep, bool _bPredicate, bool _bParseToSDBC ) 167 :rLocale(_rLocale) 168 ,aMetaData( _rxConnection ) 169 ,pParser( NULL ) 170 ,pSubQueryHistory( new QueryNameSet ) 171 ,xFormatter(_xFormatter) 172 ,xField(_xField) 173 ,m_rContext( _pContext ? (const IParseContext&)(*_pContext) : (const IParseContext&)OSQLParser::s_aDefaultContext ) 174 ,cDecSep(_cDecSep) 175 ,bQuote(_bQuote) 176 ,bInternational(_bIntl) 177 ,bPredicate(_bPredicate) 178 ,bParseToSDBCLevel( _bParseToSDBC ) 179 { 180 } 181 182 //----------------------------------------------------------------------------- 183 SQLParseNodeParameter::~SQLParseNodeParameter() 184 { 185 } 186 187 //============================================================================= 188 //= OSQLParseNode 189 //============================================================================= 190 //----------------------------------------------------------------------------- 191 ::rtl::OUString OSQLParseNode::convertDateString(const SQLParseNodeParameter& rParam, const ::rtl::OUString& rString) const 192 { 193 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::convertDateString" ); 194 Date aDate = DBTypeConversion::toDate(rString); 195 Reference< XNumberFormatsSupplier > xSupplier(rParam.xFormatter->getNumberFormatsSupplier()); 196 Reference< XNumberFormatTypes > xTypes(xSupplier->getNumberFormats(), UNO_QUERY); 197 198 double fDate = DBTypeConversion::toDouble(aDate,DBTypeConversion::getNULLDate(xSupplier)); 199 sal_Int32 nKey = xTypes->getStandardIndex(rParam.rLocale) + 36; // XXX hack 200 return rParam.xFormatter->convertNumberToString(nKey, fDate); 201 } 202 203 //----------------------------------------------------------------------------- 204 ::rtl::OUString OSQLParseNode::convertDateTimeString(const SQLParseNodeParameter& rParam, const ::rtl::OUString& rString) const 205 { 206 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::convertDateTimeString" ); 207 DateTime aDate = DBTypeConversion::toDateTime(rString); 208 Reference< XNumberFormatsSupplier > xSupplier(rParam.xFormatter->getNumberFormatsSupplier()); 209 Reference< XNumberFormatTypes > xTypes(xSupplier->getNumberFormats(), UNO_QUERY); 210 211 double fDateTime = DBTypeConversion::toDouble(aDate,DBTypeConversion::getNULLDate(xSupplier)); 212 sal_Int32 nKey = xTypes->getStandardIndex(rParam.rLocale) + 51; // XXX hack 213 return rParam.xFormatter->convertNumberToString(nKey, fDateTime); 214 } 215 216 //----------------------------------------------------------------------------- 217 ::rtl::OUString OSQLParseNode::convertTimeString(const SQLParseNodeParameter& rParam, const ::rtl::OUString& rString) const 218 { 219 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::convertTimeString" ); 220 Time aTime = DBTypeConversion::toTime(rString); 221 Reference< XNumberFormatsSupplier > xSupplier(rParam.xFormatter->getNumberFormatsSupplier()); 222 223 Reference< XNumberFormatTypes > xTypes(xSupplier->getNumberFormats(), UNO_QUERY); 224 225 double fTime = DBTypeConversion::toDouble(aTime); 226 sal_Int32 nKey = xTypes->getStandardIndex(rParam.rLocale) + 41; // XXX hack 227 return rParam.xFormatter->convertNumberToString(nKey, fTime); 228 } 229 230 //----------------------------------------------------------------------------- 231 void OSQLParseNode::parseNodeToStr(::rtl::OUString& rString, 232 const Reference< XConnection >& _rxConnection, 233 const IParseContext* pContext, 234 sal_Bool _bIntl, 235 sal_Bool _bQuote) const 236 { 237 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::parseNodeToStr" ); 238 239 parseNodeToStr( 240 rString, _rxConnection, NULL, NULL, 241 pContext ? pContext->getPreferredLocale() : OParseContext::getDefaultLocale(), 242 pContext, _bIntl, _bQuote, '.', false, false ); 243 } 244 245 //----------------------------------------------------------------------------- 246 void OSQLParseNode::parseNodeToPredicateStr(::rtl::OUString& rString, 247 const Reference< XConnection >& _rxConnection, 248 const Reference< XNumberFormatter > & xFormatter, 249 const ::com::sun::star::lang::Locale& rIntl, 250 sal_Char _cDec, 251 const IParseContext* pContext ) const 252 { 253 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::parseNodeToPredicateStr" ); 254 255 OSL_ENSURE(xFormatter.is(), "OSQLParseNode::parseNodeToPredicateStr:: no formatter!"); 256 257 if (xFormatter.is()) 258 parseNodeToStr(rString, _rxConnection, xFormatter, NULL, rIntl, pContext, sal_True, sal_True, _cDec, true, false); 259 } 260 261 //----------------------------------------------------------------------------- 262 void OSQLParseNode::parseNodeToPredicateStr(::rtl::OUString& rString, 263 const Reference< XConnection > & _rxConnection, 264 const Reference< XNumberFormatter > & xFormatter, 265 const Reference< XPropertySet > & _xField, 266 const ::com::sun::star::lang::Locale& rIntl, 267 sal_Char _cDec, 268 const IParseContext* pContext ) const 269 { 270 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::parseNodeToPredicateStr" ); 271 272 OSL_ENSURE(xFormatter.is(), "OSQLParseNode::parseNodeToPredicateStr:: no formatter!"); 273 274 if (xFormatter.is()) 275 parseNodeToStr( rString, _rxConnection, xFormatter, _xField, rIntl, pContext, true, true, _cDec, true, false ); 276 } 277 278 //----------------------------------------------------------------------------- 279 void OSQLParseNode::parseNodeToStr(::rtl::OUString& rString, 280 const Reference< XConnection > & _rxConnection, 281 const Reference< XNumberFormatter > & xFormatter, 282 const Reference< XPropertySet > & _xField, 283 const ::com::sun::star::lang::Locale& rIntl, 284 const IParseContext* pContext, 285 bool _bIntl, 286 bool _bQuote, 287 sal_Char _cDecSep, 288 bool _bPredicate, 289 bool _bSubstitute) const 290 { 291 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::parseNodeToStr" ); 292 293 OSL_ENSURE( _rxConnection.is(), "OSQLParseNode::parseNodeToStr: invalid connection!" ); 294 295 if ( _rxConnection.is() ) 296 { 297 ::rtl::OUStringBuffer sBuffer = rString; 298 try 299 { 300 OSQLParseNode::impl_parseNodeToString_throw( sBuffer, 301 SQLParseNodeParameter( 302 _rxConnection, xFormatter, _xField, rIntl, pContext, 303 _bIntl, _bQuote, _cDecSep, _bPredicate, _bSubstitute 304 ) ); 305 } 306 catch( const SQLException& ) 307 { 308 OSL_ENSURE( false, "OSQLParseNode::parseNodeToStr: this should not throw!" ); 309 // our callers don't expect this method to throw anything. The only known situation 310 // where impl_parseNodeToString_throw can throw is when there is a cyclic reference 311 // in the sub queries, but this cannot be the case here, as we do not parse to 312 // SDBC level. 313 } 314 rString = sBuffer.makeStringAndClear(); 315 } 316 } 317 //----------------------------------------------------------------------------- 318 bool OSQLParseNode::parseNodeToExecutableStatement( ::rtl::OUString& _out_rString, const Reference< XConnection >& _rxConnection, 319 OSQLParser& _rParser, ::com::sun::star::sdbc::SQLException* _pErrorHolder ) const 320 { 321 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::parseNodeToExecutableStatement" ); 322 OSL_PRECOND( _rxConnection.is(), "OSQLParseNode::parseNodeToExecutableStatement: invalid connection!" ); 323 SQLParseNodeParameter aParseParam( _rxConnection, 324 NULL, NULL, OParseContext::getDefaultLocale(), NULL, false, true, '.', false, true ); 325 326 if ( aParseParam.aMetaData.supportsSubqueriesInFrom() ) 327 { 328 Reference< XQueriesSupplier > xSuppQueries( _rxConnection, UNO_QUERY ); 329 OSL_ENSURE( xSuppQueries.is(), "OSQLParseNode::parseNodeToExecutableStatement: cannot substitute everything without a QueriesSupplier!" ); 330 if ( xSuppQueries.is() ) 331 aParseParam.xQueries = xSuppQueries->getQueries(); 332 } 333 334 aParseParam.pParser = &_rParser; 335 336 _out_rString = ::rtl::OUString(); 337 ::rtl::OUStringBuffer sBuffer; 338 bool bSuccess = false; 339 try 340 { 341 impl_parseNodeToString_throw( sBuffer, aParseParam ); 342 bSuccess = true; 343 } 344 catch( const SQLException& e ) 345 { 346 if ( _pErrorHolder ) 347 *_pErrorHolder = e; 348 } 349 _out_rString = sBuffer.makeStringAndClear(); 350 return bSuccess; 351 } 352 353 //----------------------------------------------------------------------------- 354 namespace 355 { 356 bool lcl_isAliasNamePresent( const OSQLParseNode& _rTableNameNode ) 357 { 358 return OSQLParseNode::getTableRange(_rTableNameNode.getParent()).getLength() != 0; 359 } 360 } 361 362 //----------------------------------------------------------------------------- 363 void OSQLParseNode::impl_parseNodeToString_throw(::rtl::OUStringBuffer& rString, const SQLParseNodeParameter& rParam) const 364 { 365 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::getTableRange" ); 366 if ( isToken() ) 367 { 368 parseLeaf(rString,rParam); 369 return; 370 } 371 372 // einmal auswerten wieviel Subtrees dieser Knoten besitzt 373 sal_uInt32 nCount = count(); 374 375 bool bHandled = false; 376 switch ( getKnownRuleID() ) 377 { 378 // special handling for parameters 379 case parameter: 380 { 381 if(rString.getLength()) 382 rString.appendAscii(" "); 383 if (nCount == 1) // ? 384 m_aChildren[0]->impl_parseNodeToString_throw( rString, rParam ); 385 else if (nCount == 2) // :Name 386 { 387 m_aChildren[0]->impl_parseNodeToString_throw( rString, rParam ); 388 rString.append(m_aChildren[1]->m_aNodeValue); 389 } // [Name] 390 else 391 { 392 m_aChildren[0]->impl_parseNodeToString_throw( rString, rParam ); 393 rString.append(m_aChildren[1]->m_aNodeValue); 394 rString.append(m_aChildren[2]->m_aNodeValue); 395 } 396 bHandled = true; 397 } 398 break; 399 400 // table refs 401 case table_ref: 402 if ( ( nCount == 2 ) || ( nCount == 3 ) || ( nCount == 5 ) ) 403 { 404 impl_parseTableRangeNodeToString_throw( rString, rParam ); 405 bHandled = true; 406 } 407 break; 408 409 // table name - might be a query name 410 case table_name: 411 bHandled = impl_parseTableNameNodeToString_throw( rString, rParam ); 412 break; 413 414 case as: 415 if ( rParam.aMetaData.generateASBeforeCorrelationName() ) 416 rString.append(::rtl::OUString::createFromAscii( " AS" )); 417 bHandled = true; 418 break; 419 420 case like_predicate: 421 // je nachdem ob international angegeben wird oder nicht wird like anders behandelt 422 // interanational: *, ? sind Platzhalter 423 // sonst SQL92 konform: %, _ 424 impl_parseLikeNodeToString_throw( rString, rParam ); 425 bHandled = true; 426 break; 427 428 case general_set_fct: 429 case set_fct_spec: 430 case position_exp: 431 case extract_exp: 432 case length_exp: 433 case char_value_fct: 434 { 435 if (!addDateValue(rString, rParam)) 436 { 437 // Funktionsname nicht quoten 438 SQLParseNodeParameter aNewParam(rParam); 439 aNewParam.bQuote = ( SQL_ISRULE(this,length_exp) || SQL_ISRULE(this,char_value_fct) ); 440 441 m_aChildren[0]->impl_parseNodeToString_throw( rString, aNewParam ); 442 aNewParam.bQuote = rParam.bQuote; 443 //aNewParam.bPredicate = sal_False; // disable [ ] around names // look at i73215 444 ::rtl::OUStringBuffer aStringPara; 445 for (sal_uInt32 i=1; i<nCount; i++) 446 { 447 const OSQLParseNode * pSubTree = m_aChildren[i]; 448 if (pSubTree) 449 { 450 pSubTree->impl_parseNodeToString_throw( aStringPara, aNewParam ); 451 452 // bei den CommaListen zwischen alle Subtrees Commas setzen 453 if ((m_eNodeType == SQL_NODE_COMMALISTRULE) && (i < (nCount - 1))) 454 aStringPara.appendAscii(","); 455 } 456 else 457 i++; 458 } 459 rString.append(aStringPara.makeStringAndClear()); 460 } 461 bHandled = true; 462 } 463 break; 464 default: 465 break; 466 } // switch ( getKnownRuleID() ) 467 468 if ( !bHandled ) 469 { 470 for (OSQLParseNodes::const_iterator i = m_aChildren.begin(); 471 i != m_aChildren.end();) 472 { 473 const OSQLParseNode* pSubTree = *i; 474 if ( !pSubTree ) 475 { 476 ++i; 477 continue; 478 } 479 480 SQLParseNodeParameter aNewParam(rParam); 481 482 // don't replace the field for subqueries 483 if (rParam.xField.is() && SQL_ISRULE(pSubTree,subquery)) 484 aNewParam.xField = NULL; 485 486 // if there is a field given we don't display the fieldname, if there is any 487 if (rParam.xField.is() && SQL_ISRULE(pSubTree,column_ref)) 488 { 489 sal_Bool bFilter = sal_False; 490 // retrieve the fields name 491 ::rtl::OUString aFieldName; 492 try 493 { 494 sal_Int32 nNamePropertyId = PROPERTY_ID_NAME; 495 if ( rParam.xField->getPropertySetInfo()->hasPropertyByName( OMetaConnection::getPropMap().getNameByIndex( PROPERTY_ID_REALNAME ) ) ) 496 nNamePropertyId = PROPERTY_ID_REALNAME; 497 rParam.xField->getPropertyValue( OMetaConnection::getPropMap().getNameByIndex( nNamePropertyId ) ) >>= aFieldName; 498 } 499 catch ( Exception& ) 500 { 501 } 502 503 if(pSubTree->count()) 504 { 505 const OSQLParseNode* pCol = pSubTree->m_aChildren[pSubTree->count()-1]; 506 if ( ( SQL_ISRULE(pCol,column_val) 507 && pCol->getChild(0)->getTokenValue().equalsIgnoreAsciiCase(aFieldName) 508 ) 509 || pCol->getTokenValue().equalsIgnoreAsciiCase(aFieldName) 510 ) 511 bFilter = sal_True; 512 } 513 514 // ok we found the field, if the following node is the 515 // comparison operator '=' we filter it as well 516 if (bFilter) 517 { 518 if (SQL_ISRULE(this, comparison_predicate)) 519 { 520 ++i; 521 if(i != m_aChildren.end()) 522 { 523 pSubTree = *i; 524 if (pSubTree && pSubTree->getNodeType() == SQL_NODE_EQUAL) 525 i++; 526 } 527 } 528 else 529 i++; 530 } 531 else 532 { 533 pSubTree->impl_parseNodeToString_throw( rString, aNewParam ); 534 i++; 535 536 // bei den CommaListen zwischen alle Subtrees Commas setzen 537 if ((m_eNodeType == SQL_NODE_COMMALISTRULE) && (i != m_aChildren.end())) 538 rString.appendAscii(","); 539 } 540 } 541 else 542 { 543 pSubTree->impl_parseNodeToString_throw( rString, aNewParam ); 544 i++; 545 546 // bei den CommaListen zwischen alle Subtrees Commas setzen 547 if ((m_eNodeType == SQL_NODE_COMMALISTRULE) && (i != m_aChildren.end())) 548 { 549 if (SQL_ISRULE(this,value_exp_commalist) && rParam.bPredicate) 550 rString.appendAscii(";"); 551 else 552 rString.appendAscii(","); 553 } 554 } 555 } 556 } 557 } 558 559 //----------------------------------------------------------------------------- 560 bool OSQLParseNode::impl_parseTableNameNodeToString_throw( ::rtl::OUStringBuffer& rString, const SQLParseNodeParameter& rParam ) const 561 { 562 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::impl_parseTableNameNodeToString_throw" ); 563 // is the table_name part of a table_ref? 564 OSL_ENSURE( getParent(), "OSQLParseNode::impl_parseTableNameNodeToString_throw: table_name without parent?" ); 565 if ( !getParent() || ( getParent()->getKnownRuleID() != table_ref ) ) 566 return false; 567 568 // if it's a query, maybe we need to substitute the SQL statement ... 569 if ( !rParam.bParseToSDBCLevel ) 570 return false; 571 572 if ( !rParam.xQueries.is() ) 573 // connection does not support queries in queries, or was no query supplier 574 return false; 575 576 try 577 { 578 ::rtl::OUString sTableOrQueryName( getChild(0)->getTokenValue() ); 579 bool bIsQuery = rParam.xQueries->hasByName( sTableOrQueryName ); 580 if ( !bIsQuery ) 581 return false; 582 583 // avoid recursion (e.g. "foo" defined as "SELECT * FROM bar" and "bar" defined as "SELECT * FROM foo". 584 if ( rParam.pSubQueryHistory->find( sTableOrQueryName ) != rParam.pSubQueryHistory->end() ) 585 { 586 ::rtl::OUString sMessage( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "cyclic sub queries" ) ) ); 587 OSL_ENSURE( rParam.pParser, "OSQLParseNode::impl_parseTableNameNodeToString_throw: no parser?" ); 588 if ( rParam.pParser ) 589 { 590 const SQLError& rErrors( rParam.pParser->getErrorHelper() ); 591 rErrors.raiseException( sdb::ErrorCondition::PARSER_CYCLIC_SUB_QUERIES ); 592 } 593 else 594 { 595 SQLError aErrors( ::comphelper::getProcessServiceFactory() ); 596 aErrors.raiseException( sdb::ErrorCondition::PARSER_CYCLIC_SUB_QUERIES ); 597 } 598 } 599 rParam.pSubQueryHistory->insert( sTableOrQueryName ); 600 601 Reference< XPropertySet > xQuery( rParam.xQueries->getByName( sTableOrQueryName ), UNO_QUERY_THROW ); 602 603 // substitute the query name with the constituting command 604 ::rtl::OUString sCommand; 605 OSL_VERIFY( xQuery->getPropertyValue( OMetaConnection::getPropMap().getNameByIndex( PROPERTY_ID_COMMAND ) ) >>= sCommand ); 606 607 sal_Bool bEscapeProcessing = sal_False; 608 OSL_VERIFY( xQuery->getPropertyValue( OMetaConnection::getPropMap().getNameByIndex( PROPERTY_ID_ESCAPEPROCESSING ) ) >>= bEscapeProcessing ); 609 610 // the query we found here might itself be based on another query, so parse it recursively 611 OSL_ENSURE( rParam.pParser, "OSQLParseNode::impl_parseTableNameNodeToString_throw: cannot analyze sub queries without a parser!" ); 612 if ( bEscapeProcessing && rParam.pParser ) 613 { 614 ::rtl::OUString sError; 615 ::std::auto_ptr< OSQLParseNode > pSubQueryNode( rParam.pParser->parseTree( sError, sCommand, sal_False ) ); 616 if ( pSubQueryNode.get() ) 617 { 618 // parse the sub-select to SDBC level, too 619 ::rtl::OUStringBuffer sSubSelect; 620 pSubQueryNode->impl_parseNodeToString_throw( sSubSelect, rParam ); 621 if ( sSubSelect.getLength() ) 622 sCommand = sSubSelect.makeStringAndClear(); 623 } 624 } 625 626 rString.appendAscii( " ( " ); 627 rString.append(sCommand); 628 rString.appendAscii( " )" ); 629 630 // append the query name as table alias, since it might be referenced in other 631 // parts of the statement - but only if there's no other alias name present 632 if ( !lcl_isAliasNamePresent( *this ) ) 633 { 634 rString.appendAscii( " AS " ); 635 if ( rParam.bQuote ) 636 rString.append(SetQuotation( sTableOrQueryName, 637 rParam.aMetaData.getIdentifierQuoteString(), rParam.aMetaData.getIdentifierQuoteString() )); 638 } 639 640 // don't forget to remove the query name from the history, else multiple inclusions 641 // won't work 642 // #i69227# / 2006-10-10 / frank.schoenheit@sun.com 643 rParam.pSubQueryHistory->erase( sTableOrQueryName ); 644 645 return true; 646 } 647 catch( const SQLException& ) 648 { 649 throw; 650 } 651 catch( const Exception& ) 652 { 653 DBG_UNHANDLED_EXCEPTION(); 654 } 655 return false; 656 } 657 658 //----------------------------------------------------------------------------- 659 void OSQLParseNode::impl_parseTableRangeNodeToString_throw(::rtl::OUStringBuffer& rString, const SQLParseNodeParameter& rParam) const 660 { 661 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::impl_parseTableRangeNodeToString_throw" ); 662 OSL_PRECOND( ( count() == 2 ) || ( count() == 3 ) || ( count() == 5 ) ,"Illegal count"); 663 664 // rString += ::rtl::OUString::createFromAscii(" "); 665 ::std::for_each(m_aChildren.begin(),m_aChildren.end(), 666 boost::bind( &OSQLParseNode::impl_parseNodeToString_throw, _1, boost::ref( rString ), boost::cref( rParam ) )); 667 } 668 669 //----------------------------------------------------------------------------- 670 void OSQLParseNode::impl_parseLikeNodeToString_throw( ::rtl::OUStringBuffer& rString, const SQLParseNodeParameter& rParam ) const 671 { 672 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::impl_parseLikeNodeToString_throw" ); 673 OSL_ENSURE(count() == 2,"count != 2: Prepare for GPF"); 674 675 const OSQLParseNode* pEscNode = NULL; 676 const OSQLParseNode* pParaNode = NULL; 677 678 SQLParseNodeParameter aNewParam(rParam); 679 //aNewParam.bQuote = sal_True; // why setting this to true? @see http://www.openoffice.org/issues/show_bug.cgi?id=75557 680 681 // if there is a field given we don't display the fieldname, if there are any 682 sal_Bool bAddName = sal_True; 683 if (rParam.xField.is()) 684 { 685 // retrieve the fields name 686 ::rtl::OUString aFieldName; 687 try 688 { 689 // retrieve the fields name 690 rtl::OUString aString; 691 rParam.xField->getPropertyValue(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_NAME)) >>= aString; 692 aFieldName = aString.getStr(); 693 } 694 catch ( Exception& ) 695 { 696 OSL_ENSURE( false, "OSQLParseNode::impl_parseLikeNodeToString_throw Exception occurred!" ); 697 } 698 if ( !m_aChildren[0]->isLeaf() ) 699 { 700 const OSQLParseNode* pCol = m_aChildren[0]->getChild(m_aChildren[0]->count()-1); 701 if ((SQL_ISRULE(pCol,column_val) && pCol->getChild(0)->getTokenValue().equalsIgnoreAsciiCase(aFieldName)) || 702 pCol->getTokenValue().equalsIgnoreAsciiCase(aFieldName) ) 703 bAddName = sal_False; 704 } 705 } 706 707 if (bAddName) 708 m_aChildren[0]->impl_parseNodeToString_throw( rString, aNewParam ); 709 710 const OSQLParseNode* pPart2 = m_aChildren[1]; 711 pPart2->getChild(0)->impl_parseNodeToString_throw( rString, aNewParam ); 712 pPart2->getChild(1)->impl_parseNodeToString_throw( rString, aNewParam ); 713 pParaNode = pPart2->getChild(2); 714 pEscNode = pPart2->getChild(3); 715 716 if (pParaNode->isToken()) 717 { 718 ::rtl::OUString aStr = ConvertLikeToken(pParaNode, pEscNode, rParam.bInternational); 719 rString.appendAscii(" "); 720 rString.append(SetQuotation(aStr,::rtl::OUString::createFromAscii("\'"),::rtl::OUString::createFromAscii("\'\'"))); 721 } 722 else 723 pParaNode->impl_parseNodeToString_throw( rString, aNewParam ); 724 725 pEscNode->impl_parseNodeToString_throw( rString, aNewParam ); 726 } 727 728 729 // ----------------------------------------------------------------------------- 730 sal_Bool OSQLParseNode::getTableComponents(const OSQLParseNode* _pTableNode, 731 ::com::sun::star::uno::Any &_rCatalog, 732 ::rtl::OUString &_rSchema, 733 ::rtl::OUString &_rTable, 734 const Reference< XDatabaseMetaData >& _xMetaData) 735 { 736 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::getTableComponents" ); 737 OSL_ENSURE(_pTableNode,"Wrong use of getTableComponents! _pTableNode is not allowed to be null!"); 738 if(_pTableNode) 739 { 740 const sal_Bool bSupportsCatalog = _xMetaData.is() && _xMetaData->supportsCatalogsInDataManipulation(); 741 const sal_Bool bSupportsSchema = _xMetaData.is() && _xMetaData->supportsSchemasInDataManipulation(); 742 const OSQLParseNode* pTableNode = _pTableNode; 743 // clear the parameter given 744 _rCatalog = Any(); 745 _rSchema = _rTable = ::rtl::OUString(); 746 // see rule catalog_name: in sqlbison.y 747 if (SQL_ISRULE(pTableNode,catalog_name)) 748 { 749 OSL_ENSURE(pTableNode->getChild(0) && pTableNode->getChild(0)->isToken(),"Invalid parsenode!"); 750 _rCatalog <<= pTableNode->getChild(0)->getTokenValue(); 751 pTableNode = pTableNode->getChild(2); 752 } 753 // check if we have schema_name rule 754 if(SQL_ISRULE(pTableNode,schema_name)) 755 { 756 if ( bSupportsCatalog && !bSupportsSchema ) 757 _rCatalog <<= pTableNode->getChild(0)->getTokenValue(); 758 else 759 _rSchema = pTableNode->getChild(0)->getTokenValue(); 760 pTableNode = pTableNode->getChild(2); 761 } 762 // check if we have table_name rule 763 if(SQL_ISRULE(pTableNode,table_name)) 764 { 765 _rTable = pTableNode->getChild(0)->getTokenValue(); 766 } 767 else 768 { 769 OSL_ENSURE(0,"Error in parse tree!"); 770 } 771 } 772 return _rTable.getLength() != 0; 773 } 774 // ----------------------------------------------------------------------------- 775 void OSQLParser::killThousandSeparator(OSQLParseNode* pLiteral) 776 { 777 if ( pLiteral ) 778 { 779 if ( s_xLocaleData->getLocaleItem( m_pData->aLocale ).decimalSeparator.toChar() == ',' ) 780 { 781 pLiteral->m_aNodeValue = pLiteral->m_aNodeValue.replace('.', sal_Unicode()); 782 // and replace decimal 783 pLiteral->m_aNodeValue = pLiteral->m_aNodeValue.replace(',', '.'); 784 } 785 else 786 pLiteral->m_aNodeValue = pLiteral->m_aNodeValue.replace(',', sal_Unicode()); 787 } 788 } 789 // ----------------------------------------------------------------------------- 790 OSQLParseNode* OSQLParser::convertNode(sal_Int32 nType,OSQLParseNode*& pLiteral) 791 { 792 if ( !pLiteral ) 793 return NULL; 794 795 OSQLParseNode* pReturn = pLiteral; 796 797 if ( ( pLiteral->isRule() && !SQL_ISRULE(pLiteral,value_exp) ) || SQL_ISTOKEN(pLiteral,FALSE) || SQL_ISTOKEN(pLiteral,TRUE) ) 798 { 799 switch(nType) 800 { 801 case DataType::CHAR: 802 case DataType::VARCHAR: 803 case DataType::LONGVARCHAR: 804 case DataType::CLOB: 805 if ( !SQL_ISRULE(pReturn,char_value_exp) && !buildStringNodes(pReturn) ) 806 pReturn = NULL; 807 default: 808 break; 809 } 810 } 811 else 812 { 813 switch(pLiteral->getNodeType()) 814 { 815 case SQL_NODE_STRING: 816 switch(nType) 817 { 818 case DataType::CHAR: 819 case DataType::VARCHAR: 820 case DataType::LONGVARCHAR: 821 case DataType::CLOB: 822 break; 823 case DataType::DATE: 824 case DataType::TIME: 825 case DataType::TIMESTAMP: 826 if (m_xFormatter.is()) 827 pReturn = buildDate( nType, pReturn); 828 break; 829 default: 830 m_sErrorMessage = m_pContext->getErrorMessage(IParseContext::ERROR_INVALID_COMPARE); 831 break; 832 } 833 break; 834 case SQL_NODE_ACCESS_DATE: 835 switch(nType) 836 { 837 case DataType::DATE: 838 case DataType::TIME: 839 case DataType::TIMESTAMP: 840 if ( m_xFormatter.is() ) 841 pReturn = buildDate( nType, pReturn); 842 else 843 m_sErrorMessage = m_pContext->getErrorMessage(IParseContext::ERROR_INVALID_DATE_COMPARE); 844 break; 845 default: 846 m_sErrorMessage = m_pContext->getErrorMessage(IParseContext::ERROR_INVALID_COMPARE); 847 break; 848 } 849 break; 850 case SQL_NODE_INTNUM: 851 switch(nType) 852 { 853 case DataType::BIT: 854 case DataType::BOOLEAN: 855 case DataType::DECIMAL: 856 case DataType::NUMERIC: 857 case DataType::TINYINT: 858 case DataType::SMALLINT: 859 case DataType::INTEGER: 860 case DataType::BIGINT: 861 case DataType::FLOAT: 862 case DataType::REAL: 863 case DataType::DOUBLE: 864 // kill thousand seperators if any 865 killThousandSeparator(pReturn); 866 break; 867 case DataType::CHAR: 868 case DataType::VARCHAR: 869 case DataType::LONGVARCHAR: 870 case DataType::CLOB: 871 pReturn = buildNode_STR_NUM(pReturn); 872 break; 873 default: 874 m_sErrorMessage = m_pContext->getErrorMessage(IParseContext::ERROR_INVALID_INT_COMPARE); 875 break; 876 } 877 break; 878 case SQL_NODE_APPROXNUM: 879 switch(nType) 880 { 881 case DataType::DECIMAL: 882 case DataType::NUMERIC: 883 case DataType::FLOAT: 884 case DataType::REAL: 885 case DataType::DOUBLE: 886 // kill thousand seperators if any 887 killThousandSeparator(pReturn); 888 break; 889 case DataType::CHAR: 890 case DataType::VARCHAR: 891 case DataType::LONGVARCHAR: 892 case DataType::CLOB: 893 pReturn = buildNode_STR_NUM(pReturn); 894 break; 895 case DataType::INTEGER: 896 default: 897 m_sErrorMessage = m_pContext->getErrorMessage(IParseContext::ERROR_INVALID_REAL_COMPARE); 898 break; 899 } 900 break; 901 default: 902 ; 903 } 904 } 905 return pReturn; 906 } 907 // ----------------------------------------------------------------------------- 908 sal_Int16 OSQLParser::buildPredicateRule(OSQLParseNode*& pAppend,OSQLParseNode* pLiteral,OSQLParseNode*& pCompare,OSQLParseNode* pLiteral2) 909 { 910 OSL_ENSURE(inPredicateCheck(),"Only in predicate check allowed!"); 911 sal_Int16 nErg = 0; 912 if ( m_xField.is() ) 913 { 914 sal_Int32 nType = 0; 915 try 916 { 917 m_xField->getPropertyValue(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_TYPE)) >>= nType; 918 } 919 catch( Exception& ) 920 { 921 return nErg; 922 } 923 924 OSQLParseNode* pNode1 = convertNode(nType,pLiteral); 925 if ( pNode1 ) 926 { 927 OSQLParseNode* pNode2 = convertNode(nType,pLiteral2); 928 if ( !m_sErrorMessage.getLength() ) 929 nErg = buildNode(pAppend,pCompare,pNode1,pNode2); 930 } 931 } 932 if (!pCompare->getParent()) // I have no parent so I was not used and I must die :-) 933 delete pCompare; 934 return nErg; 935 } 936 // ----------------------------------------------------------------------------- 937 sal_Int16 OSQLParser::buildLikeRule(OSQLParseNode*& pAppend, OSQLParseNode*& pLiteral, const OSQLParseNode* pEscape) 938 { 939 sal_Int16 nErg = 0; 940 sal_Int32 nType = 0; 941 942 if (!m_xField.is()) 943 return nErg; 944 try 945 { 946 Any aValue; 947 { 948 aValue = m_xField->getPropertyValue(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_TYPE)); 949 aValue >>= nType; 950 } 951 } 952 catch( Exception& ) 953 { 954 return nErg; 955 } 956 957 switch (nType) 958 { 959 case DataType::CHAR: 960 case DataType::VARCHAR: 961 case DataType::LONGVARCHAR: 962 case DataType::CLOB: 963 if(pLiteral->isRule()) 964 { 965 pAppend->append(pLiteral); 966 nErg = 1; 967 } 968 else 969 { 970 switch(pLiteral->getNodeType()) 971 { 972 case SQL_NODE_STRING: 973 pLiteral->m_aNodeValue = ConvertLikeToken(pLiteral, pEscape, sal_False); 974 pAppend->append(pLiteral); 975 nErg = 1; 976 break; 977 case SQL_NODE_APPROXNUM: 978 if (m_xFormatter.is() && m_nFormatKey) 979 { 980 sal_Int16 nScale = 0; 981 try 982 { 983 Any aValue = getNumberFormatProperty( m_xFormatter, m_nFormatKey, ::rtl::OUString::createFromAscii("Decimals") ); 984 aValue >>= nScale; 985 } 986 catch( Exception& ) 987 { 988 } 989 990 pAppend->append(new OSQLInternalNode(stringToDouble(pLiteral->getTokenValue(),nScale),SQL_NODE_STRING)); 991 } 992 else 993 pAppend->append(new OSQLInternalNode(pLiteral->getTokenValue(),SQL_NODE_STRING)); 994 995 delete pLiteral; 996 nErg = 1; 997 break; 998 default: 999 m_sErrorMessage = m_pContext->getErrorMessage(IParseContext::ERROR_VALUE_NO_LIKE); 1000 m_sErrorMessage = m_sErrorMessage.replaceAt(m_sErrorMessage.indexOf(::rtl::OUString::createFromAscii("#1")),2,pLiteral->getTokenValue()); 1001 break; 1002 } 1003 } 1004 break; 1005 default: 1006 m_sErrorMessage = m_pContext->getErrorMessage(IParseContext::ERROR_FIELD_NO_LIKE); 1007 break; 1008 } 1009 return nErg; 1010 } 1011 //----------------------------------------------------------------------------- 1012 OSQLParseNode* OSQLParser::buildNode_Date(const double& fValue, sal_Int32 nType) 1013 { 1014 ::rtl::OUString aEmptyString; 1015 OSQLParseNode* pNewNode = new OSQLInternalNode(aEmptyString, SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::set_fct_spec)); 1016 pNewNode->append(new OSQLInternalNode(::rtl::OUString::createFromAscii("{"), SQL_NODE_PUNCTUATION)); 1017 OSQLParseNode* pDateNode = new OSQLInternalNode(aEmptyString, SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::odbc_fct_spec)); 1018 pNewNode->append(pDateNode); 1019 pNewNode->append(new OSQLInternalNode(::rtl::OUString::createFromAscii("}"), SQL_NODE_PUNCTUATION)); 1020 1021 switch (nType) 1022 { 1023 case DataType::DATE: 1024 { 1025 Date aDate = DBTypeConversion::toDate(fValue,DBTypeConversion::getNULLDate(m_xFormatter->getNumberFormatsSupplier())); 1026 ::rtl::OUString aString = DBTypeConversion::toDateString(aDate); 1027 pDateNode->append(new OSQLInternalNode(aEmptyString, SQL_NODE_KEYWORD, SQL_TOKEN_D)); 1028 pDateNode->append(new OSQLInternalNode(aString, SQL_NODE_STRING)); 1029 break; 1030 } 1031 case DataType::TIME: 1032 { 1033 Time aTime = DBTypeConversion::toTime(fValue); 1034 ::rtl::OUString aString = DBTypeConversion::toTimeString(aTime); 1035 pDateNode->append(new OSQLInternalNode(aEmptyString, SQL_NODE_KEYWORD, SQL_TOKEN_T)); 1036 pDateNode->append(new OSQLInternalNode(aString, SQL_NODE_STRING)); 1037 break; 1038 } 1039 case DataType::TIMESTAMP: 1040 { 1041 DateTime aDateTime = DBTypeConversion::toDateTime(fValue,DBTypeConversion::getNULLDate(m_xFormatter->getNumberFormatsSupplier())); 1042 if (aDateTime.Seconds || aDateTime.Minutes || aDateTime.Hours) 1043 { 1044 ::rtl::OUString aString = DBTypeConversion::toDateTimeString(aDateTime); 1045 pDateNode->append(new OSQLInternalNode(aEmptyString, SQL_NODE_KEYWORD, SQL_TOKEN_TS)); 1046 pDateNode->append(new OSQLInternalNode(aString, SQL_NODE_STRING)); 1047 } 1048 else 1049 { 1050 Date aDate(aDateTime.Day,aDateTime.Month,aDateTime.Year); 1051 pDateNode->append(new OSQLInternalNode(aEmptyString, SQL_NODE_KEYWORD, SQL_TOKEN_D)); 1052 pDateNode->append(new OSQLInternalNode(DBTypeConversion::toDateString(aDate), SQL_NODE_STRING)); 1053 } 1054 break; 1055 } 1056 } 1057 1058 return pNewNode; 1059 } 1060 // ----------------------------------------------------------------------------- 1061 OSQLParseNode* OSQLParser::buildNode_STR_NUM(OSQLParseNode*& _pLiteral) 1062 { 1063 OSQLParseNode* pReturn = NULL; 1064 if ( _pLiteral ) 1065 { 1066 if (m_nFormatKey) 1067 { 1068 sal_Int16 nScale = 0; 1069 ::rtl::OUString aDec; 1070 try 1071 { 1072 Any aValue = getNumberFormatProperty( m_xFormatter, m_nFormatKey, ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Decimals")) ); 1073 aValue >>= nScale; 1074 } 1075 catch( Exception& ) 1076 { 1077 } 1078 1079 pReturn = new OSQLInternalNode(stringToDouble(_pLiteral->getTokenValue(),nScale),SQL_NODE_STRING); 1080 } 1081 else 1082 pReturn = new OSQLInternalNode(_pLiteral->getTokenValue(),SQL_NODE_STRING); 1083 1084 delete _pLiteral; 1085 _pLiteral = NULL; 1086 } 1087 return pReturn; 1088 } 1089 // ----------------------------------------------------------------------------- 1090 ::rtl::OUString OSQLParser::stringToDouble(const ::rtl::OUString& _rValue,sal_Int16 _nScale) 1091 { 1092 ::rtl::OUString aValue; 1093 if(!m_xCharClass.is()) 1094 m_xCharClass = Reference<XCharacterClassification>(m_xServiceFactory->createInstance(::rtl::OUString::createFromAscii("com.sun.star.i18n.CharacterClassification")),UNO_QUERY); 1095 if(m_xCharClass.is() && s_xLocaleData.is()) 1096 { 1097 try 1098 { 1099 ParseResult aResult = m_xCharClass->parsePredefinedToken(KParseType::ANY_NUMBER,_rValue,0,m_pData->aLocale,0,::rtl::OUString(),KParseType::ANY_NUMBER,::rtl::OUString()); 1100 if((aResult.TokenType & KParseType::IDENTNAME) && aResult.EndPos == _rValue.getLength()) 1101 { 1102 aValue = ::rtl::OUString::valueOf(aResult.Value); 1103 sal_Int32 nPos = aValue.lastIndexOf(::rtl::OUString::createFromAscii(".")); 1104 if((nPos+_nScale) < aValue.getLength()) 1105 aValue = aValue.replaceAt(nPos+_nScale,aValue.getLength()-nPos-_nScale,::rtl::OUString()); 1106 aValue = aValue.replaceAt(aValue.lastIndexOf(::rtl::OUString::createFromAscii(".")),1,s_xLocaleData->getLocaleItem(m_pData->aLocale).decimalSeparator); 1107 return aValue; 1108 } 1109 } 1110 catch(Exception&) 1111 { 1112 } 1113 } 1114 return aValue; 1115 } 1116 // ----------------------------------------------------------------------------- 1117 1118 ::osl::Mutex& OSQLParser::getMutex() 1119 { 1120 static ::osl::Mutex aMutex; 1121 return aMutex; 1122 } 1123 1124 //----------------------------------------------------------------------------- 1125 OSQLParseNode* OSQLParser::predicateTree(::rtl::OUString& rErrorMessage, const ::rtl::OUString& rStatement, 1126 const Reference< ::com::sun::star::util::XNumberFormatter > & xFormatter, 1127 const Reference< XPropertySet > & xField) 1128 { 1129 1130 1131 // mutex for parsing 1132 static ::osl::Mutex aMutex; 1133 1134 // Guard the parsing 1135 ::osl::MutexGuard aGuard(getMutex()); 1136 // must be reset 1137 setParser(this); 1138 1139 1140 // reset the parser 1141 m_xField = xField; 1142 m_xFormatter = xFormatter; 1143 1144 if (m_xField.is()) 1145 { 1146 sal_Int32 nType=0; 1147 try 1148 { 1149 // get the field name 1150 rtl::OUString aString; 1151 1152 // retrieve the fields name 1153 // #75243# use the RealName of the column if there is any otherwise the name which could be the alias 1154 // of the field 1155 Reference< XPropertySetInfo> xInfo = m_xField->getPropertySetInfo(); 1156 if ( xInfo->hasPropertyByName(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_REALNAME))) 1157 m_xField->getPropertyValue(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_REALNAME)) >>= aString; 1158 else 1159 m_xField->getPropertyValue(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_NAME)) >>= aString; 1160 1161 m_sFieldName = aString; 1162 1163 // get the field format key 1164 if ( xInfo->hasPropertyByName(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_FORMATKEY))) 1165 m_xField->getPropertyValue(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_FORMATKEY)) >>= m_nFormatKey; 1166 else 1167 m_nFormatKey = 0; 1168 1169 // get the field type 1170 m_xField->getPropertyValue(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_TYPE)) >>= nType; 1171 } 1172 catch ( Exception& ) 1173 { 1174 OSL_ASSERT(0); 1175 } 1176 1177 if (m_nFormatKey && m_xFormatter.is()) 1178 { 1179 Any aValue = getNumberFormatProperty( m_xFormatter, m_nFormatKey, OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_LOCALE) ); 1180 OSL_ENSURE(aValue.getValueType() == ::getCppuType((const ::com::sun::star::lang::Locale*)0), "OSQLParser::PredicateTree : invalid language property !"); 1181 1182 if (aValue.getValueType() == ::getCppuType((const ::com::sun::star::lang::Locale*)0)) 1183 aValue >>= m_pData->aLocale; 1184 } 1185 else 1186 m_pData->aLocale = m_pContext->getPreferredLocale(); 1187 1188 if ( m_xFormatter.is() ) 1189 { 1190 try 1191 { 1192 Reference< ::com::sun::star::util::XNumberFormatsSupplier > xFormatSup = m_xFormatter->getNumberFormatsSupplier(); 1193 if ( xFormatSup.is() ) 1194 { 1195 Reference< ::com::sun::star::util::XNumberFormats > xFormats = xFormatSup->getNumberFormats(); 1196 if ( xFormats.is() ) 1197 { 1198 ::com::sun::star::lang::Locale aLocale; 1199 aLocale.Language = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("en")); 1200 aLocale.Country = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("US")); 1201 ::rtl::OUString sFormat(RTL_CONSTASCII_USTRINGPARAM("YYYY-MM-DD")); 1202 m_nDateFormatKey = xFormats->queryKey(sFormat,aLocale,sal_False); 1203 if ( m_nDateFormatKey == sal_Int32(-1) ) 1204 m_nDateFormatKey = xFormats->addNew(sFormat, aLocale); 1205 } 1206 } 1207 } 1208 catch ( Exception& ) 1209 { 1210 OSL_ENSURE(0,"DateFormatKey"); 1211 } 1212 } 1213 1214 switch (nType) 1215 { 1216 case DataType::DATE: 1217 case DataType::TIME: 1218 case DataType::TIMESTAMP: 1219 s_pScanner->SetRule(s_pScanner->GetDATERule()); 1220 break; 1221 case DataType::CHAR: 1222 case DataType::VARCHAR: 1223 case DataType::LONGVARCHAR: 1224 case DataType::CLOB: 1225 s_pScanner->SetRule(s_pScanner->GetSTRINGRule()); 1226 break; 1227 default: 1228 if ( s_xLocaleData->getLocaleItem( m_pData->aLocale ).decimalSeparator.toChar() == ',' ) 1229 s_pScanner->SetRule(s_pScanner->GetGERRule()); 1230 else 1231 s_pScanner->SetRule(s_pScanner->GetENGRule()); 1232 } 1233 1234 } 1235 else 1236 s_pScanner->SetRule(s_pScanner->GetSQLRule()); 1237 1238 s_pScanner->prepareScan(rStatement, m_pContext, sal_True); 1239 1240 SQLyylval.pParseNode = NULL; 1241 // SQLyypvt = NULL; 1242 m_pParseTree = NULL; 1243 m_sErrorMessage= ::rtl::OUString(); 1244 1245 // ... und den Parser anwerfen ... 1246 if (SQLyyparse() != 0) 1247 { 1248 m_sFieldName= ::rtl::OUString(); 1249 m_xField.clear(); 1250 m_xFormatter.clear(); 1251 m_nFormatKey = 0; 1252 m_nDateFormatKey = 0; 1253 1254 if (!m_sErrorMessage.getLength()) 1255 m_sErrorMessage = s_pScanner->getErrorMessage(); 1256 if (!m_sErrorMessage.getLength()) 1257 m_sErrorMessage = m_pContext->getErrorMessage(IParseContext::ERROR_GENERAL); 1258 1259 rErrorMessage = m_sErrorMessage; 1260 1261 // clear the garbage collector 1262 (*s_pGarbageCollector)->clearAndDelete(); 1263 return NULL; 1264 } 1265 else 1266 { 1267 (*s_pGarbageCollector)->clear(); 1268 1269 m_sFieldName= ::rtl::OUString(); 1270 m_xField.clear(); 1271 m_xFormatter.clear(); 1272 m_nFormatKey = 0; 1273 m_nDateFormatKey = 0; 1274 1275 // Das Ergebnis liefern (den Root Parse Node): 1276 1277 // Stattdessen setzt die Parse-Routine jetzt den Member pParseTree 1278 // - einfach diesen zurueckliefern: 1279 OSL_ENSURE(m_pParseTree != NULL,"OSQLParser: Parser hat keinen ParseTree geliefert"); 1280 return m_pParseTree; 1281 } 1282 } 1283 1284 //============================================================================= 1285 //----------------------------------------------------------------------------- 1286 OSQLParser::OSQLParser(const ::com::sun::star::uno::Reference< ::com::sun::star::lang::XMultiServiceFactory >& _xServiceFactory,const IParseContext* _pContext) 1287 :m_pContext(_pContext) 1288 ,m_pParseTree(NULL) 1289 ,m_pData( new OSQLParser_Data( _xServiceFactory ) ) 1290 ,m_nFormatKey(0) 1291 ,m_nDateFormatKey(0) 1292 ,m_xServiceFactory(_xServiceFactory) 1293 { 1294 1295 1296 setParser(this); 1297 1298 #ifdef SQLYYDEBUG 1299 #ifdef SQLYYDEBUG_ON 1300 SQLyydebug = 1; 1301 #endif 1302 #endif 1303 1304 ::osl::MutexGuard aGuard(getMutex()); 1305 // do we have to initialize the data 1306 if (s_nRefCount == 0) 1307 { 1308 s_pScanner = new OSQLScanner(); 1309 s_pScanner->setScanner(); 1310 s_pGarbageCollector = new OSQLParseNodesGarbageCollector(); 1311 1312 if(!s_xLocaleData.is()) 1313 s_xLocaleData = Reference<XLocaleData>(m_xServiceFactory->createInstance(::rtl::OUString::createFromAscii("com.sun.star.i18n.LocaleData")),UNO_QUERY); 1314 1315 // auf 0 zuruecksetzen 1316 memset(OSQLParser::s_nRuleIDs,0,sizeof(OSQLParser::s_nRuleIDs[0]) * (OSQLParseNode::rule_count+1)); 1317 1318 struct 1319 { 1320 OSQLParseNode::Rule eRule; // the parse node's ID for the rule 1321 ::rtl::OString sRuleName; // the name of the rule ("select_statement") 1322 } aRuleDescriptions[] = 1323 { 1324 { OSQLParseNode::select_statement, "select_statement" }, 1325 { OSQLParseNode::table_exp, "table_exp" }, 1326 { OSQLParseNode::table_ref_commalist, "table_ref_commalist" }, 1327 { OSQLParseNode::table_ref, "table_ref" }, 1328 { OSQLParseNode::catalog_name, "catalog_name" }, 1329 { OSQLParseNode::schema_name, "schema_name" }, 1330 { OSQLParseNode::table_name, "table_name" }, 1331 { OSQLParseNode::opt_column_commalist, "opt_column_commalist" }, 1332 { OSQLParseNode::column_commalist, "column_commalist" }, 1333 { OSQLParseNode::column_ref_commalist, "column_ref_commalist" }, 1334 { OSQLParseNode::column_ref, "column_ref" }, 1335 { OSQLParseNode::opt_order_by_clause, "opt_order_by_clause" }, 1336 { OSQLParseNode::ordering_spec_commalist, "ordering_spec_commalist" }, 1337 { OSQLParseNode::ordering_spec, "ordering_spec" }, 1338 { OSQLParseNode::opt_asc_desc, "opt_asc_desc" }, 1339 { OSQLParseNode::where_clause, "where_clause" }, 1340 { OSQLParseNode::opt_where_clause, "opt_where_clause" }, 1341 { OSQLParseNode::search_condition, "search_condition" }, 1342 { OSQLParseNode::comparison_predicate, "comparison_predicate" }, 1343 { OSQLParseNode::between_predicate, "between_predicate" }, 1344 { OSQLParseNode::like_predicate, "like_predicate" }, 1345 { OSQLParseNode::opt_escape, "opt_escape" }, 1346 { OSQLParseNode::test_for_null, "test_for_null" }, 1347 { OSQLParseNode::scalar_exp_commalist, "scalar_exp_commalist" }, 1348 { OSQLParseNode::scalar_exp, "scalar_exp" }, 1349 { OSQLParseNode::parameter_ref, "parameter_ref" }, 1350 { OSQLParseNode::parameter, "parameter" }, 1351 { OSQLParseNode::general_set_fct, "general_set_fct" }, 1352 { OSQLParseNode::range_variable, "range_variable" }, 1353 { OSQLParseNode::column, "column" }, 1354 { OSQLParseNode::delete_statement_positioned, "delete_statement_positioned" }, 1355 { OSQLParseNode::delete_statement_searched, "delete_statement_searched" }, 1356 { OSQLParseNode::update_statement_positioned, "update_statement_positioned" }, 1357 { OSQLParseNode::update_statement_searched, "update_statement_searched" }, 1358 { OSQLParseNode::assignment_commalist, "assignment_commalist" }, 1359 { OSQLParseNode::assignment, "assignment" }, 1360 { OSQLParseNode::values_or_query_spec, "values_or_query_spec" }, 1361 { OSQLParseNode::insert_statement, "insert_statement" }, 1362 { OSQLParseNode::insert_atom_commalist, "insert_atom_commalist" }, 1363 { OSQLParseNode::insert_atom, "insert_atom" }, 1364 { OSQLParseNode::predicate_check, "predicate_check" }, 1365 { OSQLParseNode::from_clause, "from_clause" }, 1366 { OSQLParseNode::qualified_join, "qualified_join" }, 1367 { OSQLParseNode::cross_union, "cross_union" }, 1368 { OSQLParseNode::select_sublist, "select_sublist" }, 1369 { OSQLParseNode::derived_column, "derived_column" }, 1370 { OSQLParseNode::column_val, "column_val" }, 1371 { OSQLParseNode::set_fct_spec, "set_fct_spec" }, 1372 { OSQLParseNode::boolean_term, "boolean_term" }, 1373 { OSQLParseNode::boolean_primary, "boolean_primary" }, 1374 { OSQLParseNode::num_value_exp, "num_value_exp" }, 1375 { OSQLParseNode::join_type, "join_type" }, 1376 { OSQLParseNode::position_exp, "position_exp" }, 1377 { OSQLParseNode::extract_exp, "extract_exp" }, 1378 { OSQLParseNode::length_exp, "length_exp" }, 1379 { OSQLParseNode::char_value_fct, "char_value_fct" }, 1380 { OSQLParseNode::odbc_call_spec, "odbc_call_spec" }, 1381 { OSQLParseNode::in_predicate, "in_predicate" }, 1382 { OSQLParseNode::existence_test, "existence_test" }, 1383 { OSQLParseNode::unique_test, "unique_test" }, 1384 { OSQLParseNode::all_or_any_predicate, "all_or_any_predicate" }, 1385 { OSQLParseNode::named_columns_join, "named_columns_join" }, 1386 { OSQLParseNode::join_condition, "join_condition" }, 1387 { OSQLParseNode::joined_table, "joined_table" }, 1388 { OSQLParseNode::boolean_factor, "boolean_factor" }, 1389 { OSQLParseNode::sql_not, "sql_not" }, 1390 { OSQLParseNode::boolean_test, "boolean_test" }, 1391 { OSQLParseNode::manipulative_statement, "manipulative_statement" }, 1392 { OSQLParseNode::subquery, "subquery" }, 1393 { OSQLParseNode::value_exp_commalist, "value_exp_commalist" }, 1394 { OSQLParseNode::odbc_fct_spec, "odbc_fct_spec" }, 1395 { OSQLParseNode::union_statement, "union_statement" }, 1396 { OSQLParseNode::outer_join_type, "outer_join_type" }, 1397 { OSQLParseNode::char_value_exp, "char_value_exp" }, 1398 { OSQLParseNode::term, "term" }, 1399 { OSQLParseNode::value_exp_primary, "value_exp_primary" }, 1400 { OSQLParseNode::value_exp, "value_exp" }, 1401 { OSQLParseNode::selection, "selection" }, 1402 { OSQLParseNode::fold, "fold" }, 1403 { OSQLParseNode::char_substring_fct, "char_substring_fct" }, 1404 { OSQLParseNode::factor, "factor" }, 1405 { OSQLParseNode::base_table_def, "base_table_def" }, 1406 { OSQLParseNode::base_table_element_commalist, "base_table_element_commalist" }, 1407 { OSQLParseNode::data_type, "data_type" }, 1408 { OSQLParseNode::column_def, "column_def" }, 1409 { OSQLParseNode::table_node, "table_node" }, 1410 { OSQLParseNode::as, "as" }, 1411 { OSQLParseNode::op_column_commalist, "op_column_commalist" }, 1412 { OSQLParseNode::table_primary_as_range_column, "table_primary_as_range_column" }, 1413 { OSQLParseNode::datetime_primary, "datetime_primary" }, 1414 { OSQLParseNode::concatenation, "concatenation" }, 1415 { OSQLParseNode::char_factor, "char_factor" }, 1416 { OSQLParseNode::bit_value_fct, "bit_value_fct" }, 1417 { OSQLParseNode::comparison_predicate_part_2, "comparison_predicate_part_2" }, 1418 { OSQLParseNode::parenthesized_boolean_value_expression, "parenthesized_boolean_value_expression" }, 1419 { OSQLParseNode::character_string_type, "character_string_type" }, 1420 { OSQLParseNode::other_like_predicate_part_2, "other_like_predicate_part_2" }, 1421 { OSQLParseNode::between_predicate_part_2, "between_predicate_part_2" }, 1422 { OSQLParseNode::cast_spec, "cast_spec" } 1423 }; 1424 size_t nRuleMapCount = sizeof( aRuleDescriptions ) / sizeof( aRuleDescriptions[0] ); 1425 OSL_ENSURE( nRuleMapCount == size_t( OSQLParseNode::rule_count ), "OSQLParser::OSQLParser: added a new rule? Adjust this map!" ); 1426 1427 for ( size_t mapEntry = 0; mapEntry < nRuleMapCount; ++mapEntry ) 1428 { 1429 // look up the rule description in the our identifier map 1430 sal_uInt32 nParserRuleID = StrToRuleID( aRuleDescriptions[ mapEntry ].sRuleName ); 1431 // map the parser's rule ID to the OSQLParseNode::Rule 1432 s_aReverseRuleIDLookup[ nParserRuleID ] = aRuleDescriptions[ mapEntry ].eRule; 1433 // and map the OSQLParseNode::Rule to the parser's rule ID 1434 s_nRuleIDs[ aRuleDescriptions[ mapEntry ].eRule ] = nParserRuleID; 1435 } 1436 } 1437 ++s_nRefCount; 1438 1439 if (m_pContext == NULL) 1440 // take the default context 1441 m_pContext = &s_aDefaultContext; 1442 1443 m_pData->aLocale = m_pContext->getPreferredLocale(); 1444 } 1445 1446 //----------------------------------------------------------------------------- 1447 OSQLParser::~OSQLParser() 1448 { 1449 { 1450 ::osl::MutexGuard aGuard(getMutex()); 1451 OSL_ENSURE(s_nRefCount > 0, "OSQLParser::~OSQLParser() : suspicious call : have a refcount of 0 !"); 1452 if (!--s_nRefCount) 1453 { 1454 s_pScanner->setScanner(sal_True); 1455 delete s_pScanner; 1456 s_pScanner = NULL; 1457 1458 delete s_pGarbageCollector; 1459 s_pGarbageCollector = NULL; 1460 // is only set the first time so we should delete it only when there no more instances 1461 s_xLocaleData = NULL; 1462 1463 RuleIDMap aEmpty; 1464 s_aReverseRuleIDLookup.swap( aEmpty ); 1465 } 1466 m_pParseTree = NULL; 1467 } 1468 } 1469 // ----------------------------------------------------------------------------- 1470 void OSQLParseNode::substituteParameterNames(OSQLParseNode* _pNode) 1471 { 1472 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::substituteParameterNames" ); 1473 sal_Int32 nCount = _pNode->count(); 1474 for(sal_Int32 i=0;i < nCount;++i) 1475 { 1476 OSQLParseNode* pChildNode = _pNode->getChild(i); 1477 if(SQL_ISRULE(pChildNode,parameter) && pChildNode->count() > 1) 1478 { 1479 OSQLParseNode* pNewNode = new OSQLParseNode(::rtl::OUString::createFromAscii("?") ,SQL_NODE_PUNCTUATION,0); 1480 delete pChildNode->replace(pChildNode->getChild(0),pNewNode); 1481 sal_Int32 nChildCount = pChildNode->count(); 1482 for(sal_Int32 j=1;j < nChildCount;++j) 1483 delete pChildNode->removeAt(1); 1484 } 1485 else 1486 substituteParameterNames(pChildNode); 1487 1488 } 1489 } 1490 // ----------------------------------------------------------------------------- 1491 bool OSQLParser::extractDate(OSQLParseNode* pLiteral,double& _rfValue) 1492 { 1493 Reference< XNumberFormatsSupplier > xFormatSup = m_xFormatter->getNumberFormatsSupplier(); 1494 Reference< XNumberFormatTypes > xFormatTypes; 1495 if ( xFormatSup.is() ) 1496 xFormatTypes = xFormatTypes.query( xFormatSup->getNumberFormats() ); 1497 1498 // if there is no format key, yet, make sure we have a feasible one for our locale 1499 try 1500 { 1501 if ( !m_nFormatKey && xFormatTypes.is() ) 1502 m_nFormatKey = ::dbtools::getDefaultNumberFormat( m_xField, xFormatTypes, m_pData->aLocale ); 1503 } 1504 catch( Exception& ) { } 1505 ::rtl::OUString sValue = pLiteral->getTokenValue(); 1506 sal_Int32 nTryFormat = m_nFormatKey; 1507 bool bSuccess = lcl_saveConvertToNumber( m_xFormatter, nTryFormat, sValue, _rfValue ); 1508 1509 // If our format key didn't do, try the default date format for our locale. 1510 if ( !bSuccess && xFormatTypes.is() ) 1511 { 1512 try 1513 { 1514 nTryFormat = xFormatTypes->getStandardFormat( NumberFormat::DATE, m_pData->aLocale ); 1515 } 1516 catch( Exception& ) { } 1517 bSuccess = lcl_saveConvertToNumber( m_xFormatter, nTryFormat, sValue, _rfValue ); 1518 } 1519 1520 // if this also didn't do, try ISO format 1521 if ( !bSuccess && xFormatTypes.is() ) 1522 { 1523 try 1524 { 1525 nTryFormat = xFormatTypes->getFormatIndex( NumberFormatIndex::DATE_DIN_YYYYMMDD, m_pData->aLocale ); 1526 } 1527 catch( Exception& ) { } 1528 bSuccess = lcl_saveConvertToNumber( m_xFormatter, nTryFormat, sValue, _rfValue ); 1529 } 1530 1531 // if this also didn't do, try fallback date format (en-US) 1532 if ( !bSuccess ) 1533 { 1534 nTryFormat = m_nDateFormatKey; 1535 bSuccess = lcl_saveConvertToNumber( m_xFormatter, nTryFormat, sValue, _rfValue ); 1536 } 1537 return bSuccess; 1538 } 1539 // ----------------------------------------------------------------------------- 1540 OSQLParseNode* OSQLParser::buildDate(sal_Int32 _nType,OSQLParseNode*& pLiteral) 1541 { 1542 // try converting the string into a date, according to our format key 1543 double fValue = 0.0; 1544 OSQLParseNode* pFCTNode = NULL; 1545 1546 if ( extractDate(pLiteral,fValue) ) 1547 pFCTNode = buildNode_Date( fValue, _nType); 1548 1549 delete pLiteral; 1550 pLiteral = NULL; 1551 1552 if ( !pFCTNode ) 1553 m_sErrorMessage = m_pContext->getErrorMessage(IParseContext::ERROR_INVALID_DATE_COMPARE); 1554 1555 return pFCTNode; 1556 } 1557 // ----------------------------------------------------------------------------- 1558 //----------------------------------------------------------------------------- 1559 OSQLParseNode::OSQLParseNode(const sal_Char * pNewValue, 1560 SQLNodeType eNewNodeType, 1561 sal_uInt32 nNewNodeID) 1562 :m_pParent(NULL) 1563 ,m_aNodeValue(pNewValue,strlen(pNewValue),RTL_TEXTENCODING_UTF8) 1564 ,m_eNodeType(eNewNodeType) 1565 ,m_nNodeID(nNewNodeID) 1566 { 1567 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::OSQLParseNode" ); 1568 1569 OSL_ENSURE(m_eNodeType >= SQL_NODE_RULE && m_eNodeType <= SQL_NODE_CONCAT,"OSQLParseNode: mit unzulaessigem NodeType konstruiert"); 1570 } 1571 //----------------------------------------------------------------------------- 1572 OSQLParseNode::OSQLParseNode(const ::rtl::OString &_rNewValue, 1573 SQLNodeType eNewNodeType, 1574 sal_uInt32 nNewNodeID) 1575 :m_pParent(NULL) 1576 ,m_aNodeValue( rtl::OStringToOUString( _rNewValue, RTL_TEXTENCODING_UTF8)) 1577 ,m_eNodeType(eNewNodeType) 1578 ,m_nNodeID(nNewNodeID) 1579 { 1580 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::OSQLParseNode" ); 1581 1582 OSL_ENSURE(m_eNodeType >= SQL_NODE_RULE && m_eNodeType <= SQL_NODE_CONCAT,"OSQLParseNode: mit unzulaessigem NodeType konstruiert"); 1583 } 1584 //----------------------------------------------------------------------------- 1585 OSQLParseNode::OSQLParseNode(const sal_Unicode * pNewValue, 1586 SQLNodeType eNewNodeType, 1587 sal_uInt32 nNewNodeID) 1588 :m_pParent(NULL) 1589 ,m_aNodeValue(pNewValue) 1590 ,m_eNodeType(eNewNodeType) 1591 ,m_nNodeID(nNewNodeID) 1592 { 1593 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::OSQLParseNode" ); 1594 1595 OSL_ENSURE(m_eNodeType >= SQL_NODE_RULE && m_eNodeType <= SQL_NODE_CONCAT,"OSQLParseNode: mit unzulaessigem NodeType konstruiert"); 1596 } 1597 //----------------------------------------------------------------------------- 1598 OSQLParseNode::OSQLParseNode(const ::rtl::OUString &_rNewValue, 1599 SQLNodeType eNewNodeType, 1600 sal_uInt32 nNewNodeID) 1601 :m_pParent(NULL) 1602 ,m_aNodeValue(_rNewValue) 1603 ,m_eNodeType(eNewNodeType) 1604 ,m_nNodeID(nNewNodeID) 1605 { 1606 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::OSQLParseNode" ); 1607 1608 OSL_ENSURE(m_eNodeType >= SQL_NODE_RULE && m_eNodeType <= SQL_NODE_CONCAT,"OSQLParseNode: mit unzulaessigem NodeType konstruiert"); 1609 } 1610 //----------------------------------------------------------------------------- 1611 OSQLParseNode::OSQLParseNode(const OSQLParseNode& rParseNode) 1612 { 1613 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::OSQLParseNode" ); 1614 1615 // klemm den getParent auf NULL 1616 m_pParent = NULL; 1617 1618 // kopiere die member 1619 m_aNodeValue = rParseNode.m_aNodeValue; 1620 m_eNodeType = rParseNode.m_eNodeType; 1621 m_nNodeID = rParseNode.m_nNodeID; 1622 1623 1624 // denk dran, dass von Container abgeleitet wurde, laut SV-Help erzeugt 1625 // copy-Constructor des Containers einen neuen Container mit den gleichen 1626 // Zeigern als Inhalt -> d.h. nach dem Kopieren des Container wird fuer 1627 // alle Zeiger ungleich NULL eine Kopie hergestellt und anstelle des alten 1628 // Zeigers wieder eingehangen. 1629 1630 // wenn kein Blatt, dann SubTrees bearbeiten 1631 for (OSQLParseNodes::const_iterator i = rParseNode.m_aChildren.begin(); 1632 i != rParseNode.m_aChildren.end(); i++) 1633 append(new OSQLParseNode(**i)); 1634 } 1635 // ----------------------------------------------------------------------------- 1636 //----------------------------------------------------------------------------- 1637 OSQLParseNode& OSQLParseNode::operator=(const OSQLParseNode& rParseNode) 1638 { 1639 if (this != &rParseNode) 1640 { 1641 // kopiere die member - pParent bleibt der alte 1642 m_aNodeValue = rParseNode.m_aNodeValue; 1643 m_eNodeType = rParseNode.m_eNodeType; 1644 m_nNodeID = rParseNode.m_nNodeID; 1645 1646 for (OSQLParseNodes::const_iterator i = m_aChildren.begin(); 1647 i != m_aChildren.end(); i++) 1648 delete *i; 1649 1650 m_aChildren.clear(); 1651 1652 for (OSQLParseNodes::const_iterator j = rParseNode.m_aChildren.begin(); 1653 j != rParseNode.m_aChildren.end(); j++) 1654 append(new OSQLParseNode(**j)); 1655 } 1656 return *this; 1657 } 1658 1659 //----------------------------------------------------------------------------- 1660 sal_Bool OSQLParseNode::operator==(OSQLParseNode& rParseNode) const 1661 { 1662 // die member muessen gleich sein 1663 sal_Bool bResult = (m_nNodeID == rParseNode.m_nNodeID) && 1664 (m_eNodeType == rParseNode.m_eNodeType) && 1665 (m_aNodeValue == rParseNode.m_aNodeValue) && 1666 count() == rParseNode.count(); 1667 1668 // Parameters are not equal! 1669 bResult = bResult && !SQL_ISRULE(this, parameter); 1670 1671 // compare childs 1672 for (sal_uInt32 i=0; bResult && i < count(); i++) 1673 bResult = *getChild(i) == *rParseNode.getChild(i); 1674 1675 return bResult; 1676 } 1677 1678 //----------------------------------------------------------------------------- 1679 OSQLParseNode::~OSQLParseNode() 1680 { 1681 for (OSQLParseNodes::const_iterator i = m_aChildren.begin(); 1682 i != m_aChildren.end(); i++) 1683 delete *i; 1684 m_aChildren.clear(); 1685 } 1686 1687 //----------------------------------------------------------------------------- 1688 void OSQLParseNode::append(OSQLParseNode* pNewNode) 1689 { 1690 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::append" ); 1691 1692 OSL_ENSURE(pNewNode != NULL, "OSQLParseNode: ungueltiger NewSubTree"); 1693 OSL_ENSURE(pNewNode->getParent() == NULL, "OSQLParseNode: Knoten ist kein Waise"); 1694 OSL_ENSURE(::std::find(m_aChildren.begin(), m_aChildren.end(), pNewNode) == m_aChildren.end(), 1695 "OSQLParseNode::append() Node already element of parent"); 1696 1697 // stelle Verbindung zum getParent her: 1698 pNewNode->setParent( this ); 1699 // und haenge den SubTree hinten an 1700 m_aChildren.push_back(pNewNode); 1701 } 1702 // ----------------------------------------------------------------------------- 1703 sal_Bool OSQLParseNode::addDateValue(::rtl::OUStringBuffer& rString, const SQLParseNodeParameter& rParam) const 1704 { 1705 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::addDateValue" ); 1706 // special display for date/time values 1707 if (SQL_ISRULE(this,set_fct_spec) && SQL_ISPUNCTUATION(m_aChildren[0],"{")) 1708 { 1709 const OSQLParseNode* pODBCNode = m_aChildren[1]; 1710 const OSQLParseNode* pODBCNodeChild = pODBCNode->m_aChildren[0]; 1711 1712 if (pODBCNodeChild->getNodeType() == SQL_NODE_KEYWORD && ( 1713 SQL_ISTOKEN(pODBCNodeChild, D) || 1714 SQL_ISTOKEN(pODBCNodeChild, T) || 1715 SQL_ISTOKEN(pODBCNodeChild, TS) )) 1716 { 1717 ::rtl::OUString suQuote(::rtl::OUString::createFromAscii("'")); 1718 if (rParam.bPredicate) 1719 { 1720 if (rParam.aMetaData.shouldEscapeDateTime()) 1721 { 1722 suQuote = ::rtl::OUString::createFromAscii("#"); 1723 } 1724 } 1725 else 1726 { 1727 if (rParam.aMetaData.shouldEscapeDateTime()) 1728 { 1729 // suQuote = ::rtl::OUString::createFromAscii("'"); 1730 return sal_False; 1731 } 1732 } 1733 1734 if (rString.getLength()) 1735 rString.appendAscii(" "); 1736 rString.append(suQuote); 1737 const ::rtl::OUString sTokenValue = pODBCNode->m_aChildren[1]->getTokenValue(); 1738 if (SQL_ISTOKEN(pODBCNodeChild, D)) 1739 { 1740 rString.append(rParam.bPredicate ? convertDateString(rParam, sTokenValue) : sTokenValue); 1741 } 1742 else if (SQL_ISTOKEN(pODBCNodeChild, T)) 1743 { 1744 rString.append(rParam.bPredicate ? convertTimeString(rParam, sTokenValue) : sTokenValue); 1745 } 1746 else 1747 { 1748 rString.append(rParam.bPredicate ? convertDateTimeString(rParam, sTokenValue) : sTokenValue); 1749 } 1750 rString.append(suQuote); 1751 return sal_True; 1752 } 1753 } 1754 return sal_False; 1755 } 1756 // ----------------------------------------------------------------------------- 1757 void OSQLParseNode::replaceNodeValue(const ::rtl::OUString& rTableAlias,const ::rtl::OUString& rColumnName) 1758 { 1759 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::replaceNodeValue" ); 1760 for (sal_uInt32 i=0;i<count();++i) 1761 { 1762 if (SQL_ISRULE(this,column_ref) && count() == 1 && getChild(0)->getTokenValue() == rColumnName) 1763 { 1764 OSQLParseNode * pCol = removeAt((sal_uInt32)0); 1765 append(new OSQLParseNode(rTableAlias,SQL_NODE_NAME)); 1766 append(new OSQLParseNode(::rtl::OUString::createFromAscii("."),SQL_NODE_PUNCTUATION)); 1767 append(pCol); 1768 } 1769 else 1770 getChild(i)->replaceNodeValue(rTableAlias,rColumnName); 1771 } 1772 } 1773 //----------------------------------------------------------------------------- 1774 OSQLParseNode* OSQLParseNode::getByRule(OSQLParseNode::Rule eRule) const 1775 { 1776 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::getByRule" ); 1777 OSQLParseNode* pRetNode = 0; 1778 if (isRule() && OSQLParser::RuleID(eRule) == getRuleID()) 1779 pRetNode = (OSQLParseNode*)this; 1780 else 1781 { 1782 for (OSQLParseNodes::const_iterator i = m_aChildren.begin(); 1783 !pRetNode && i != m_aChildren.end(); i++) 1784 pRetNode = (*i)->getByRule(eRule); 1785 } 1786 return pRetNode; 1787 } 1788 //----------------------------------------------------------------------------- 1789 OSQLParseNode* MakeANDNode(OSQLParseNode *pLeftLeaf,OSQLParseNode *pRightLeaf) 1790 { 1791 OSQLParseNode* pNewNode = new OSQLParseNode(::rtl::OUString(),SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::boolean_term)); 1792 pNewNode->append(pLeftLeaf); 1793 pNewNode->append(new OSQLParseNode(::rtl::OUString::createFromAscii("AND"),SQL_NODE_KEYWORD,SQL_TOKEN_AND)); 1794 pNewNode->append(pRightLeaf); 1795 return pNewNode; 1796 } 1797 //----------------------------------------------------------------------------- 1798 OSQLParseNode* MakeORNode(OSQLParseNode *pLeftLeaf,OSQLParseNode *pRightLeaf) 1799 { 1800 OSQLParseNode* pNewNode = new OSQLParseNode(::rtl::OUString(),SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::search_condition)); 1801 pNewNode->append(pLeftLeaf); 1802 pNewNode->append(new OSQLParseNode(::rtl::OUString::createFromAscii("OR"),SQL_NODE_KEYWORD,SQL_TOKEN_OR)); 1803 pNewNode->append(pRightLeaf); 1804 return pNewNode; 1805 } 1806 //----------------------------------------------------------------------------- 1807 void OSQLParseNode::disjunctiveNormalForm(OSQLParseNode*& pSearchCondition) 1808 { 1809 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::disjunctiveNormalForm" ); 1810 if(!pSearchCondition) // no where condition at entry point 1811 return; 1812 1813 OSQLParseNode::absorptions(pSearchCondition); 1814 // '(' search_condition ')' 1815 if (SQL_ISRULE(pSearchCondition,boolean_primary)) 1816 { 1817 OSQLParseNode* pLeft = pSearchCondition->getChild(1); 1818 disjunctiveNormalForm(pLeft); 1819 } 1820 // search_condition SQL_TOKEN_OR boolean_term 1821 else if (SQL_ISRULE(pSearchCondition,search_condition)) 1822 { 1823 OSQLParseNode* pLeft = pSearchCondition->getChild(0); 1824 disjunctiveNormalForm(pLeft); 1825 1826 OSQLParseNode* pRight = pSearchCondition->getChild(2); 1827 disjunctiveNormalForm(pRight); 1828 } 1829 // boolean_term SQL_TOKEN_AND boolean_factor 1830 else if (SQL_ISRULE(pSearchCondition,boolean_term)) 1831 { 1832 OSQLParseNode* pLeft = pSearchCondition->getChild(0); 1833 disjunctiveNormalForm(pLeft); 1834 1835 OSQLParseNode* pRight = pSearchCondition->getChild(2); 1836 disjunctiveNormalForm(pRight); 1837 1838 OSQLParseNode* pNewNode = NULL; 1839 // '(' search_condition ')' on left side 1840 if(pLeft->count() == 3 && SQL_ISRULE(pLeft,boolean_primary) && SQL_ISRULE(pLeft->getChild(1),search_condition)) 1841 { 1842 // and-or tree on left side 1843 OSQLParseNode* pOr = pLeft->getChild(1); 1844 OSQLParseNode* pNewLeft = NULL; 1845 OSQLParseNode* pNewRight = NULL; 1846 1847 // cut right from parent 1848 pSearchCondition->removeAt(2); 1849 1850 pNewRight = MakeANDNode(pOr->removeAt(2) ,pRight); 1851 pNewLeft = MakeANDNode(pOr->removeAt((sal_uInt32)0) ,new OSQLParseNode(*pRight)); 1852 pNewNode = MakeORNode(pNewLeft,pNewRight); 1853 // and append new Node 1854 replaceAndReset(pSearchCondition,pNewNode); 1855 1856 disjunctiveNormalForm(pSearchCondition); 1857 } 1858 else if(pRight->count() == 3 && SQL_ISRULE(pRight,boolean_primary) && SQL_ISRULE(pRight->getChild(1),search_condition)) 1859 { // '(' search_condition ')' on right side 1860 // and-or tree on right side 1861 // a and (b or c) 1862 OSQLParseNode* pOr = pRight->getChild(1); 1863 OSQLParseNode* pNewLeft = NULL; 1864 OSQLParseNode* pNewRight = NULL; 1865 1866 // cut left from parent 1867 pSearchCondition->removeAt((sal_uInt32)0); 1868 1869 pNewRight = MakeANDNode(pLeft,pOr->removeAt(2)); 1870 pNewLeft = MakeANDNode(new OSQLParseNode(*pLeft),pOr->removeAt((sal_uInt32)0)); 1871 pNewNode = MakeORNode(pNewLeft,pNewRight); 1872 1873 // and append new Node 1874 replaceAndReset(pSearchCondition,pNewNode); 1875 disjunctiveNormalForm(pSearchCondition); 1876 } 1877 else if(SQL_ISRULE(pLeft,boolean_primary) && (!SQL_ISRULE(pLeft->getChild(1),search_condition) || !SQL_ISRULE(pLeft->getChild(1),boolean_term))) 1878 pSearchCondition->replace(pLeft, pLeft->removeAt(1)); 1879 else if(SQL_ISRULE(pRight,boolean_primary) && (!SQL_ISRULE(pRight->getChild(1),search_condition) || !SQL_ISRULE(pRight->getChild(1),boolean_term))) 1880 pSearchCondition->replace(pRight, pRight->removeAt(1)); 1881 } 1882 } 1883 //----------------------------------------------------------------------------- 1884 void OSQLParseNode::negateSearchCondition(OSQLParseNode*& pSearchCondition,sal_Bool bNegate) 1885 { 1886 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::negateSearchCondition" ); 1887 if(!pSearchCondition) // no where condition at entry point 1888 return; 1889 // '(' search_condition ')' 1890 if (pSearchCondition->count() == 3 && SQL_ISRULE(pSearchCondition,boolean_primary)) 1891 { 1892 OSQLParseNode* pRight = pSearchCondition->getChild(1); 1893 negateSearchCondition(pRight,bNegate); 1894 } 1895 // search_condition SQL_TOKEN_OR boolean_term 1896 else if (SQL_ISRULE(pSearchCondition,search_condition)) 1897 { 1898 OSQLParseNode* pLeft = pSearchCondition->getChild(0); 1899 OSQLParseNode* pRight = pSearchCondition->getChild(2); 1900 if(bNegate) 1901 { 1902 OSQLParseNode* pNewNode = new OSQLParseNode(::rtl::OUString(),SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::boolean_term)); 1903 pNewNode->append(pSearchCondition->removeAt((sal_uInt32)0)); 1904 pNewNode->append(new OSQLParseNode(::rtl::OUString::createFromAscii("AND"),SQL_NODE_KEYWORD,SQL_TOKEN_AND)); 1905 pNewNode->append(pSearchCondition->removeAt((sal_uInt32)1)); 1906 replaceAndReset(pSearchCondition,pNewNode); 1907 1908 pLeft = pNewNode->getChild(0); 1909 pRight = pNewNode->getChild(2); 1910 } 1911 1912 negateSearchCondition(pLeft,bNegate); 1913 negateSearchCondition(pRight,bNegate); 1914 } 1915 // boolean_term SQL_TOKEN_AND boolean_factor 1916 else if (SQL_ISRULE(pSearchCondition,boolean_term)) 1917 { 1918 OSQLParseNode* pLeft = pSearchCondition->getChild(0); 1919 OSQLParseNode* pRight = pSearchCondition->getChild(2); 1920 if(bNegate) 1921 { 1922 OSQLParseNode* pNewNode = new OSQLParseNode(::rtl::OUString(),SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::search_condition)); 1923 pNewNode->append(pSearchCondition->removeAt((sal_uInt32)0)); 1924 pNewNode->append(new OSQLParseNode(::rtl::OUString::createFromAscii("OR"),SQL_NODE_KEYWORD,SQL_TOKEN_OR)); 1925 pNewNode->append(pSearchCondition->removeAt((sal_uInt32)1)); 1926 replaceAndReset(pSearchCondition,pNewNode); 1927 1928 pLeft = pNewNode->getChild(0); 1929 pRight = pNewNode->getChild(2); 1930 } 1931 1932 negateSearchCondition(pLeft,bNegate); 1933 negateSearchCondition(pRight,bNegate); 1934 } 1935 // SQL_TOKEN_NOT ( boolean_test ) 1936 else if (SQL_ISRULE(pSearchCondition,boolean_factor)) 1937 { 1938 OSQLParseNode *pNot = pSearchCondition->removeAt((sal_uInt32)0); 1939 delete pNot; 1940 OSQLParseNode *pBooleanTest = pSearchCondition->removeAt((sal_uInt32)0); 1941 // TODO is this needed // pBooleanTest->setParent(NULL); 1942 replaceAndReset(pSearchCondition,pBooleanTest); 1943 1944 if (!bNegate) 1945 negateSearchCondition(pSearchCondition,sal_True); // negate all deeper values 1946 } 1947 // row_value_constructor comparison row_value_constructor 1948 // row_value_constructor comparison any_all_some subquery 1949 else if(bNegate && (SQL_ISRULE(pSearchCondition,comparison_predicate) || SQL_ISRULE(pSearchCondition,all_or_any_predicate))) 1950 { 1951 OSQLParseNode* pComparison = pSearchCondition->getChild(1); 1952 OSQLParseNode* pNewComparison = NULL; 1953 switch(pComparison->getNodeType()) 1954 { 1955 case SQL_NODE_EQUAL: 1956 pNewComparison = new OSQLParseNode(::rtl::OUString::createFromAscii("<>"),SQL_NODE_NOTEQUAL,SQL_NOTEQUAL); 1957 break; 1958 case SQL_NODE_LESS: 1959 pNewComparison = new OSQLParseNode(::rtl::OUString::createFromAscii(">="),SQL_NODE_GREATEQ,SQL_GREATEQ); 1960 break; 1961 case SQL_NODE_GREAT: 1962 pNewComparison = new OSQLParseNode(::rtl::OUString::createFromAscii("<="),SQL_NODE_LESSEQ,SQL_LESSEQ); 1963 break; 1964 case SQL_NODE_LESSEQ: 1965 pNewComparison = new OSQLParseNode(::rtl::OUString::createFromAscii(">"),SQL_NODE_GREAT,SQL_GREAT); 1966 break; 1967 case SQL_NODE_GREATEQ: 1968 pNewComparison = new OSQLParseNode(::rtl::OUString::createFromAscii("<"),SQL_NODE_LESS,SQL_LESS); 1969 break; 1970 case SQL_NODE_NOTEQUAL: 1971 pNewComparison = new OSQLParseNode(::rtl::OUString::createFromAscii("="),SQL_NODE_EQUAL,SQL_EQUAL); 1972 break; 1973 default: 1974 OSL_ENSURE( false, "OSQLParseNode::negateSearchCondition: unexpected node type!" ); 1975 break; 1976 } 1977 pSearchCondition->replace(pComparison, pNewComparison); 1978 delete pComparison; 1979 } 1980 1981 else if(bNegate && (SQL_ISRULE(pSearchCondition,test_for_null) || SQL_ISRULE(pSearchCondition,in_predicate) || 1982 SQL_ISRULE(pSearchCondition,between_predicate) || SQL_ISRULE(pSearchCondition,boolean_test) )) 1983 { 1984 OSQLParseNode* pPart2 = pSearchCondition; 1985 if ( !SQL_ISRULE(pSearchCondition,boolean_test) ) 1986 pPart2 = pSearchCondition->getChild(1); 1987 sal_uInt32 nNotPos = 0; 1988 if ( SQL_ISRULE( pSearchCondition, test_for_null ) ) 1989 nNotPos = 1; 1990 else if ( SQL_ISRULE( pSearchCondition, boolean_test ) ) 1991 nNotPos = 2; 1992 1993 OSQLParseNode* pNot = pPart2->getChild(nNotPos); 1994 OSQLParseNode* pNotNot = NULL; 1995 if(pNot->isRule()) 1996 pNotNot = new OSQLParseNode(::rtl::OUString::createFromAscii("NOT"),SQL_NODE_KEYWORD,SQL_TOKEN_NOT); 1997 else 1998 pNotNot = new OSQLParseNode(::rtl::OUString(),SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::sql_not)); 1999 pPart2->replace(pNot, pNotNot); 2000 delete pNot; 2001 } 2002 else if(bNegate && (SQL_ISRULE(pSearchCondition,like_predicate))) 2003 { 2004 OSQLParseNode* pNot = pSearchCondition->getChild( 1 )->getChild( 0 ); 2005 OSQLParseNode* pNotNot = NULL; 2006 if(pNot->isRule()) 2007 pNotNot = new OSQLParseNode(::rtl::OUString::createFromAscii("NOT"),SQL_NODE_KEYWORD,SQL_TOKEN_NOT); 2008 else 2009 pNotNot = new OSQLParseNode(::rtl::OUString(),SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::sql_not)); 2010 pSearchCondition->getChild( 1 )->replace(pNot, pNotNot); 2011 delete pNot; 2012 } 2013 } 2014 //----------------------------------------------------------------------------- 2015 void OSQLParseNode::eraseBraces(OSQLParseNode*& pSearchCondition) 2016 { 2017 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::eraseBraces" ); 2018 if (pSearchCondition && (SQL_ISRULE(pSearchCondition,boolean_primary) || (pSearchCondition->count() == 3 && SQL_ISPUNCTUATION(pSearchCondition->getChild(0),"(") && 2019 SQL_ISPUNCTUATION(pSearchCondition->getChild(2),")")))) 2020 { 2021 OSQLParseNode* pRight = pSearchCondition->getChild(1); 2022 absorptions(pRight); 2023 // if child is not a or or and tree then delete () around child 2024 if(!(SQL_ISRULE(pSearchCondition->getChild(1),boolean_term) || SQL_ISRULE(pSearchCondition->getChild(1),search_condition)) || 2025 SQL_ISRULE(pSearchCondition->getChild(1),boolean_term) || // and can always stand without () 2026 (SQL_ISRULE(pSearchCondition->getChild(1),search_condition) && SQL_ISRULE(pSearchCondition->getParent(),search_condition))) 2027 { 2028 OSQLParseNode* pNode = pSearchCondition->removeAt(1); 2029 replaceAndReset(pSearchCondition,pNode); 2030 } 2031 } 2032 } 2033 //----------------------------------------------------------------------------- 2034 void OSQLParseNode::absorptions(OSQLParseNode*& pSearchCondition) 2035 { 2036 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::absorptions" ); 2037 if(!pSearchCondition) // no where condition at entry point 2038 return; 2039 2040 eraseBraces(pSearchCondition); 2041 2042 if(SQL_ISRULE(pSearchCondition,boolean_term) || SQL_ISRULE(pSearchCondition,search_condition)) 2043 { 2044 OSQLParseNode* pLeft = pSearchCondition->getChild(0); 2045 absorptions(pLeft); 2046 OSQLParseNode* pRight = pSearchCondition->getChild(2); 2047 absorptions(pRight); 2048 } 2049 2050 sal_uInt32 nPos = 0; 2051 // a and a || a or a 2052 OSQLParseNode* pNewNode = NULL; 2053 if(( SQL_ISRULE(pSearchCondition,boolean_term) || SQL_ISRULE(pSearchCondition,search_condition)) 2054 && *pSearchCondition->getChild(0) == *pSearchCondition->getChild(2)) 2055 { 2056 pNewNode = pSearchCondition->removeAt((sal_uInt32)0); 2057 replaceAndReset(pSearchCondition,pNewNode); 2058 } 2059 // (a or b) and a || ( b or c ) and a 2060 // a and ( a or b) || a and ( b or c ) 2061 else if ( SQL_ISRULE(pSearchCondition,boolean_term) 2062 && ( 2063 ( SQL_ISRULE(pSearchCondition->getChild(nPos = 0),boolean_primary) 2064 || SQL_ISRULE(pSearchCondition->getChild(nPos),search_condition) 2065 ) 2066 || ( SQL_ISRULE(pSearchCondition->getChild(nPos = 2),boolean_primary) 2067 || SQL_ISRULE(pSearchCondition->getChild(nPos),search_condition) 2068 ) 2069 ) 2070 ) 2071 { 2072 OSQLParseNode* p2ndSearch = pSearchCondition->getChild(nPos); 2073 if ( SQL_ISRULE(p2ndSearch,boolean_primary) ) 2074 p2ndSearch = p2ndSearch->getChild(1); 2075 2076 if ( *p2ndSearch->getChild(0) == *pSearchCondition->getChild(2-nPos) ) // a and ( a or b) -> a or b 2077 { 2078 pNewNode = pSearchCondition->removeAt((sal_uInt32)0); 2079 replaceAndReset(pSearchCondition,pNewNode); 2080 2081 } 2082 else if ( *p2ndSearch->getChild(2) == *pSearchCondition->getChild(2-nPos) ) // a and ( b or a) -> a or b 2083 { 2084 pNewNode = pSearchCondition->removeAt((sal_uInt32)2); 2085 replaceAndReset(pSearchCondition,pNewNode); 2086 } 2087 else if ( p2ndSearch->getByRule(OSQLParseNode::search_condition) ) 2088 { 2089 // a and ( b or c ) -> ( a and b ) or ( a and c ) 2090 // ( b or c ) and a -> ( a and b ) or ( a and c ) 2091 OSQLParseNode* pC = p2ndSearch->removeAt((sal_uInt32)2); 2092 OSQLParseNode* pB = p2ndSearch->removeAt((sal_uInt32)0); 2093 OSQLParseNode* pA = pSearchCondition->removeAt((sal_uInt32)2-nPos); 2094 2095 OSQLParseNode* p1stAnd = MakeANDNode(pA,pB); 2096 OSQLParseNode* p2ndAnd = MakeANDNode(new OSQLParseNode(*pA),pC); 2097 pNewNode = MakeORNode(p1stAnd,p2ndAnd); 2098 OSQLParseNode* pNode = new OSQLParseNode(::rtl::OUString(),SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::boolean_primary)); 2099 pNode->append(new OSQLParseNode(::rtl::OUString::createFromAscii("("),SQL_NODE_PUNCTUATION)); 2100 pNode->append(pNewNode); 2101 pNode->append(new OSQLParseNode(::rtl::OUString::createFromAscii(")"),SQL_NODE_PUNCTUATION)); 2102 OSQLParseNode::eraseBraces(p1stAnd); 2103 OSQLParseNode::eraseBraces(p2ndAnd); 2104 replaceAndReset(pSearchCondition,pNode); 2105 } 2106 } 2107 // a or a and b || a or b and a 2108 else if(SQL_ISRULE(pSearchCondition,search_condition) && SQL_ISRULE(pSearchCondition->getChild(2),boolean_term)) 2109 { 2110 if(*pSearchCondition->getChild(2)->getChild(0) == *pSearchCondition->getChild(0)) 2111 { 2112 pNewNode = pSearchCondition->removeAt((sal_uInt32)0); 2113 replaceAndReset(pSearchCondition,pNewNode); 2114 } 2115 else if(*pSearchCondition->getChild(2)->getChild(2) == *pSearchCondition->getChild(0)) 2116 { 2117 pNewNode = pSearchCondition->removeAt((sal_uInt32)0); 2118 replaceAndReset(pSearchCondition,pNewNode); 2119 } 2120 } 2121 // a and b or a || b and a or a 2122 else if(SQL_ISRULE(pSearchCondition,search_condition) && SQL_ISRULE(pSearchCondition->getChild(0),boolean_term)) 2123 { 2124 if(*pSearchCondition->getChild(0)->getChild(0) == *pSearchCondition->getChild(2)) 2125 { 2126 pNewNode = pSearchCondition->removeAt((sal_uInt32)2); 2127 replaceAndReset(pSearchCondition,pNewNode); 2128 } 2129 else if(*pSearchCondition->getChild(0)->getChild(2) == *pSearchCondition->getChild(2)) 2130 { 2131 pNewNode = pSearchCondition->removeAt((sal_uInt32)2); 2132 replaceAndReset(pSearchCondition,pNewNode); 2133 } 2134 } 2135 eraseBraces(pSearchCondition); 2136 } 2137 //----------------------------------------------------------------------------- 2138 void OSQLParseNode::compress(OSQLParseNode *&pSearchCondition) 2139 { 2140 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::compress" ); 2141 if(!pSearchCondition) // no where condition at entry point 2142 return; 2143 2144 OSQLParseNode::eraseBraces(pSearchCondition); 2145 2146 if(SQL_ISRULE(pSearchCondition,boolean_term) || SQL_ISRULE(pSearchCondition,search_condition)) 2147 { 2148 OSQLParseNode* pLeft = pSearchCondition->getChild(0); 2149 compress(pLeft); 2150 2151 OSQLParseNode* pRight = pSearchCondition->getChild(2); 2152 compress(pRight); 2153 } 2154 else if( SQL_ISRULE(pSearchCondition,boolean_primary) || (pSearchCondition->count() == 3 && SQL_ISPUNCTUATION(pSearchCondition->getChild(0),"(") && 2155 SQL_ISPUNCTUATION(pSearchCondition->getChild(2),")"))) 2156 { 2157 OSQLParseNode* pRight = pSearchCondition->getChild(1); 2158 compress(pRight); 2159 // if child is not a or or and tree then delete () around child 2160 if(!(SQL_ISRULE(pSearchCondition->getChild(1),boolean_term) || SQL_ISRULE(pSearchCondition->getChild(1),search_condition)) || 2161 (SQL_ISRULE(pSearchCondition->getChild(1),boolean_term) && SQL_ISRULE(pSearchCondition->getParent(),boolean_term)) || 2162 (SQL_ISRULE(pSearchCondition->getChild(1),search_condition) && SQL_ISRULE(pSearchCondition->getParent(),search_condition))) 2163 { 2164 OSQLParseNode* pNode = pSearchCondition->removeAt(1); 2165 replaceAndReset(pSearchCondition,pNode); 2166 } 2167 } 2168 2169 // or with two and trees where one element of the and trees are equal 2170 if(SQL_ISRULE(pSearchCondition,search_condition) && SQL_ISRULE(pSearchCondition->getChild(0),boolean_term) && SQL_ISRULE(pSearchCondition->getChild(2),boolean_term)) 2171 { 2172 if(*pSearchCondition->getChild(0)->getChild(0) == *pSearchCondition->getChild(2)->getChild(0)) 2173 { 2174 OSQLParseNode* pLeft = pSearchCondition->getChild(0)->removeAt(2); 2175 OSQLParseNode* pRight = pSearchCondition->getChild(2)->removeAt(2); 2176 OSQLParseNode* pNode = MakeORNode(pLeft,pRight); 2177 2178 OSQLParseNode* pNewRule = new OSQLParseNode(::rtl::OUString(),SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::boolean_primary)); 2179 pNewRule->append(new OSQLParseNode(::rtl::OUString::createFromAscii("("),SQL_NODE_PUNCTUATION)); 2180 pNewRule->append(pNode); 2181 pNewRule->append(new OSQLParseNode(::rtl::OUString::createFromAscii(")"),SQL_NODE_PUNCTUATION)); 2182 2183 OSQLParseNode::eraseBraces(pLeft); 2184 OSQLParseNode::eraseBraces(pRight); 2185 2186 pNode = MakeANDNode(pSearchCondition->getChild(0)->removeAt((sal_uInt32)0),pNewRule); 2187 replaceAndReset(pSearchCondition,pNode); 2188 } 2189 else if(*pSearchCondition->getChild(0)->getChild(2) == *pSearchCondition->getChild(2)->getChild(0)) 2190 { 2191 OSQLParseNode* pLeft = pSearchCondition->getChild(0)->removeAt((sal_uInt32)0); 2192 OSQLParseNode* pRight = pSearchCondition->getChild(2)->removeAt(2); 2193 OSQLParseNode* pNode = MakeORNode(pLeft,pRight); 2194 2195 OSQLParseNode* pNewRule = new OSQLParseNode(::rtl::OUString(),SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::boolean_primary)); 2196 pNewRule->append(new OSQLParseNode(::rtl::OUString::createFromAscii("("),SQL_NODE_PUNCTUATION)); 2197 pNewRule->append(pNode); 2198 pNewRule->append(new OSQLParseNode(::rtl::OUString::createFromAscii(")"),SQL_NODE_PUNCTUATION)); 2199 2200 OSQLParseNode::eraseBraces(pLeft); 2201 OSQLParseNode::eraseBraces(pRight); 2202 2203 pNode = MakeANDNode(pSearchCondition->getChild(0)->removeAt(1),pNewRule); 2204 replaceAndReset(pSearchCondition,pNode); 2205 } 2206 else if(*pSearchCondition->getChild(0)->getChild(0) == *pSearchCondition->getChild(2)->getChild(2)) 2207 { 2208 OSQLParseNode* pLeft = pSearchCondition->getChild(0)->removeAt(2); 2209 OSQLParseNode* pRight = pSearchCondition->getChild(2)->removeAt((sal_uInt32)0); 2210 OSQLParseNode* pNode = MakeORNode(pLeft,pRight); 2211 2212 OSQLParseNode* pNewRule = new OSQLParseNode(::rtl::OUString(),SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::boolean_primary)); 2213 pNewRule->append(new OSQLParseNode(::rtl::OUString::createFromAscii("("),SQL_NODE_PUNCTUATION)); 2214 pNewRule->append(pNode); 2215 pNewRule->append(new OSQLParseNode(::rtl::OUString::createFromAscii(")"),SQL_NODE_PUNCTUATION)); 2216 2217 OSQLParseNode::eraseBraces(pLeft); 2218 OSQLParseNode::eraseBraces(pRight); 2219 2220 pNode = MakeANDNode(pSearchCondition->getChild(0)->removeAt((sal_uInt32)0),pNewRule); 2221 replaceAndReset(pSearchCondition,pNode); 2222 } 2223 else if(*pSearchCondition->getChild(0)->getChild(2) == *pSearchCondition->getChild(2)->getChild(2)) 2224 { 2225 OSQLParseNode* pLeft = pSearchCondition->getChild(0)->removeAt((sal_uInt32)0); 2226 OSQLParseNode* pRight = pSearchCondition->getChild(2)->removeAt((sal_uInt32)0); 2227 OSQLParseNode* pNode = MakeORNode(pLeft,pRight); 2228 2229 OSQLParseNode* pNewRule = new OSQLParseNode(::rtl::OUString(),SQL_NODE_RULE,OSQLParser::RuleID(OSQLParseNode::boolean_primary)); 2230 pNewRule->append(new OSQLParseNode(::rtl::OUString::createFromAscii("("),SQL_NODE_PUNCTUATION)); 2231 pNewRule->append(pNode); 2232 pNewRule->append(new OSQLParseNode(::rtl::OUString::createFromAscii(")"),SQL_NODE_PUNCTUATION)); 2233 2234 OSQLParseNode::eraseBraces(pLeft); 2235 OSQLParseNode::eraseBraces(pRight); 2236 2237 pNode = MakeANDNode(pSearchCondition->getChild(0)->removeAt(1),pNewRule); 2238 replaceAndReset(pSearchCondition,pNode); 2239 } 2240 } 2241 } 2242 #if OSL_DEBUG_LEVEL > 0 2243 // ----------------------------------------------------------------------------- 2244 void OSQLParseNode::showParseTree( ::rtl::OUString& rString ) const 2245 { 2246 ::rtl::OUStringBuffer aBuf; 2247 showParseTree( aBuf, 0 ); 2248 rString = aBuf.makeStringAndClear(); 2249 } 2250 2251 // ----------------------------------------------------------------------------- 2252 void OSQLParseNode::showParseTree( ::rtl::OUStringBuffer& _inout_rBuffer, sal_uInt32 nLevel ) const 2253 { 2254 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::showParseTree" ); 2255 2256 for ( sal_uInt32 j=0; j<nLevel; ++j) 2257 _inout_rBuffer.appendAscii( " " ); 2258 2259 if ( !isToken() ) 2260 { 2261 // Regelnamen als rule: ... 2262 _inout_rBuffer.appendAscii( "RULE_ID: " ); 2263 _inout_rBuffer.append( (sal_Int32)getRuleID() ); 2264 _inout_rBuffer.append( sal_Unicode( '(' ) ); 2265 _inout_rBuffer.append( OSQLParser::RuleIDToStr( getRuleID() ) ); 2266 _inout_rBuffer.append( sal_Unicode( ')' ) ); 2267 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2268 2269 // hol dir den ersten Subtree 2270 for ( OSQLParseNodes::const_iterator i = m_aChildren.begin(); 2271 i != m_aChildren.end(); 2272 ++i 2273 ) 2274 (*i)->showParseTree( _inout_rBuffer, nLevel+1 ); 2275 } 2276 else 2277 { 2278 // ein Token gefunden 2279 switch (m_eNodeType) 2280 { 2281 2282 case SQL_NODE_KEYWORD: 2283 _inout_rBuffer.appendAscii( "SQL_KEYWORD: " ); 2284 _inout_rBuffer.append( ::rtl::OStringToOUString( OSQLParser::TokenIDToStr( getTokenID() ), RTL_TEXTENCODING_UTF8 ) ); 2285 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2286 break; 2287 2288 case SQL_NODE_COMPARISON: 2289 _inout_rBuffer.appendAscii( "SQL_COMPARISON: " ); 2290 _inout_rBuffer.append( m_aNodeValue ); 2291 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2292 break; 2293 2294 case SQL_NODE_NAME: 2295 _inout_rBuffer.appendAscii( "SQL_NAME: " ); 2296 _inout_rBuffer.append( sal_Unicode( '"' ) ); 2297 _inout_rBuffer.append( m_aNodeValue ); 2298 _inout_rBuffer.append( sal_Unicode( '"' ) ); 2299 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2300 break; 2301 2302 case SQL_NODE_STRING: 2303 _inout_rBuffer.appendAscii( "SQL_STRING: " ); 2304 _inout_rBuffer.append( sal_Unicode( '\'' ) ); 2305 _inout_rBuffer.append( m_aNodeValue ); 2306 _inout_rBuffer.append( sal_Unicode( '\'' ) ); 2307 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2308 break; 2309 2310 case SQL_NODE_INTNUM: 2311 _inout_rBuffer.appendAscii( "SQL_INTNUM: " ); 2312 _inout_rBuffer.append( m_aNodeValue ); 2313 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2314 break; 2315 2316 case SQL_NODE_APPROXNUM: 2317 _inout_rBuffer.appendAscii( "SQL_APPROXNUM: " ); 2318 _inout_rBuffer.append( m_aNodeValue ); 2319 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2320 break; 2321 2322 case SQL_NODE_PUNCTUATION: 2323 _inout_rBuffer.appendAscii( "SQL_PUNCTUATION: " ); 2324 _inout_rBuffer.append( m_aNodeValue ); 2325 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2326 break; 2327 2328 case SQL_NODE_AMMSC: 2329 _inout_rBuffer.appendAscii( "SQL_AMMSC: " ); 2330 _inout_rBuffer.append( m_aNodeValue ); 2331 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2332 break; 2333 2334 case SQL_NODE_EQUAL: 2335 case SQL_NODE_LESS: 2336 case SQL_NODE_GREAT: 2337 case SQL_NODE_LESSEQ: 2338 case SQL_NODE_GREATEQ: 2339 case SQL_NODE_NOTEQUAL: 2340 _inout_rBuffer.append( m_aNodeValue ); 2341 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2342 break; 2343 2344 case SQL_NODE_ACCESS_DATE: 2345 _inout_rBuffer.appendAscii( "SQL_ACCESS_DATE: " ); 2346 _inout_rBuffer.append( m_aNodeValue ); 2347 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2348 break; 2349 2350 case SQL_NODE_DATE: 2351 _inout_rBuffer.appendAscii( "SQL_DATE: " ); 2352 _inout_rBuffer.append( m_aNodeValue ); 2353 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2354 break; 2355 2356 case SQL_NODE_CONCAT: 2357 _inout_rBuffer.appendAscii( "||" ); 2358 _inout_rBuffer.append( sal_Unicode( '\n' ) ); 2359 break; 2360 2361 default: 2362 OSL_TRACE( "-- %i", int( m_eNodeType ) ); 2363 OSL_ENSURE( false, "OSQLParser::ShowParseTree: unzulaessiger NodeType" ); 2364 } 2365 } 2366 } 2367 #endif // OSL_DEBUG_LEVEL > 0 2368 // ----------------------------------------------------------------------------- 2369 // Insert-Methoden 2370 //----------------------------------------------------------------------------- 2371 void OSQLParseNode::insert(sal_uInt32 nPos, OSQLParseNode* pNewSubTree) 2372 { 2373 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::insert" ); 2374 OSL_ENSURE(pNewSubTree != NULL, "OSQLParseNode: ungueltiger NewSubTree"); 2375 OSL_ENSURE(pNewSubTree->getParent() == NULL, "OSQLParseNode: Knoten ist kein Waise"); 2376 2377 // stelle Verbindung zum getParent her: 2378 pNewSubTree->setParent( this ); 2379 m_aChildren.insert(m_aChildren.begin() + nPos, pNewSubTree); 2380 } 2381 2382 // removeAt-Methoden 2383 //----------------------------------------------------------------------------- 2384 OSQLParseNode* OSQLParseNode::removeAt(sal_uInt32 nPos) 2385 { 2386 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::removeAt" ); 2387 OSL_ENSURE(nPos < m_aChildren.size(),"Illegal position for removeAt"); 2388 OSQLParseNodes::iterator aPos(m_aChildren.begin() + nPos); 2389 OSQLParseNode* pNode = *aPos; 2390 2391 // setze den getParent des removeten auf NULL 2392 pNode->setParent( NULL ); 2393 2394 m_aChildren.erase(aPos); 2395 return pNode; 2396 } 2397 //----------------------------------------------------------------------------- 2398 OSQLParseNode* OSQLParseNode::remove(OSQLParseNode* pSubTree) 2399 { 2400 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::remove" ); 2401 OSL_ENSURE(pSubTree != NULL, "OSQLParseNode: ungueltiger SubTree"); 2402 OSQLParseNodes::iterator aPos = ::std::find(m_aChildren.begin(), m_aChildren.end(), pSubTree); 2403 if (aPos != m_aChildren.end()) 2404 { 2405 // setze den getParent des removeten auf NULL 2406 pSubTree->setParent( NULL ); 2407 m_aChildren.erase(aPos); 2408 return pSubTree; 2409 } 2410 else 2411 return NULL; 2412 } 2413 2414 // Replace-Methoden 2415 //----------------------------------------------------------------------------- 2416 OSQLParseNode* OSQLParseNode::replaceAt(sal_uInt32 nPos, OSQLParseNode* pNewSubNode) 2417 { 2418 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::replaceAt" ); 2419 OSL_ENSURE(pNewSubNode != NULL, "OSQLParseNode: invalid nodes"); 2420 OSL_ENSURE(pNewSubNode->getParent() == NULL, "OSQLParseNode: node already has getParent"); 2421 OSL_ENSURE(nPos < m_aChildren.size(), "OSQLParseNode: invalid position"); 2422 OSL_ENSURE(::std::find(m_aChildren.begin(), m_aChildren.end(), pNewSubNode) == m_aChildren.end(), 2423 "OSQLParseNode::Replace() Node already element of parent"); 2424 2425 OSQLParseNode* pOldSubNode = m_aChildren[nPos]; 2426 2427 // stelle Verbindung zum getParent her: 2428 pNewSubNode->setParent( this ); 2429 pOldSubNode->setParent( NULL ); 2430 2431 m_aChildren[nPos] = pNewSubNode; 2432 return pOldSubNode; 2433 } 2434 2435 //----------------------------------------------------------------------------- 2436 OSQLParseNode* OSQLParseNode::replace (OSQLParseNode* pOldSubNode, OSQLParseNode* pNewSubNode ) 2437 { 2438 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::replace " ); 2439 OSL_ENSURE(pOldSubNode != NULL && pNewSubNode != NULL, "OSQLParseNode: invalid nodes"); 2440 OSL_ENSURE(pNewSubNode->getParent() == NULL, "OSQLParseNode: node already has getParent"); 2441 OSL_ENSURE(::std::find(m_aChildren.begin(), m_aChildren.end(), pOldSubNode) != m_aChildren.end(), 2442 "OSQLParseNode::Replace() Node not element of parent"); 2443 OSL_ENSURE(::std::find(m_aChildren.begin(), m_aChildren.end(), pNewSubNode) == m_aChildren.end(), 2444 "OSQLParseNode::Replace() Node already element of parent"); 2445 2446 pOldSubNode->setParent( NULL ); 2447 pNewSubNode->setParent( this ); 2448 ::std::replace(m_aChildren.begin(), m_aChildren.end(), pOldSubNode, pNewSubNode); 2449 return pOldSubNode; 2450 } 2451 // ----------------------------------------------------------------------------- 2452 void OSQLParseNode::parseLeaf(::rtl::OUStringBuffer& rString, const SQLParseNodeParameter& rParam) const 2453 { 2454 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::parseLeaf" ); 2455 // ein Blatt ist gefunden 2456 // Inhalt dem Ausgabestring anfuegen 2457 switch (m_eNodeType) 2458 { 2459 case SQL_NODE_KEYWORD: 2460 { 2461 if (rString.getLength()) 2462 rString.appendAscii(" "); 2463 2464 const ::rtl::OString sT = OSQLParser::TokenIDToStr(m_nNodeID, rParam.bInternational ? &rParam.m_rContext : NULL); 2465 rString.append( ::rtl::OStringToOUString( sT, RTL_TEXTENCODING_UTF8)); 2466 } break; 2467 case SQL_NODE_STRING: 2468 if (rString.getLength()) 2469 rString.appendAscii(" "); 2470 rString.append(SetQuotation(m_aNodeValue,::rtl::OUString::createFromAscii("\'"),::rtl::OUString::createFromAscii("\'\'"))); 2471 break; 2472 case SQL_NODE_NAME: 2473 if (rString.getLength()) 2474 { 2475 switch(rString.charAt(rString.getLength()-1) ) 2476 { 2477 case ' ' : 2478 case '.' : break; 2479 default : 2480 if ( !rParam.aMetaData.getCatalogSeparator().getLength() 2481 || rString.charAt( rString.getLength()-1 ) != rParam.aMetaData.getCatalogSeparator().toChar() 2482 ) 2483 rString.appendAscii(" "); break; 2484 } 2485 } 2486 if (rParam.bQuote) 2487 { 2488 if (rParam.bPredicate) 2489 { 2490 rString.appendAscii("["); 2491 rString.append(m_aNodeValue); 2492 rString.appendAscii("]"); 2493 } 2494 else 2495 rString.append(SetQuotation(m_aNodeValue, 2496 rParam.aMetaData.getIdentifierQuoteString(), rParam.aMetaData.getIdentifierQuoteString() )); 2497 } 2498 else 2499 rString.append(m_aNodeValue); 2500 break; 2501 case SQL_NODE_ACCESS_DATE: 2502 if (rString.getLength()) 2503 rString.appendAscii(" "); 2504 rString.appendAscii("#"); 2505 rString.append(m_aNodeValue); 2506 rString.appendAscii("#"); 2507 break; 2508 2509 case SQL_NODE_INTNUM: 2510 case SQL_NODE_APPROXNUM: 2511 { 2512 ::rtl::OUString aTmp = m_aNodeValue; 2513 if (rParam.bInternational && rParam.bPredicate && rParam.cDecSep != '.') 2514 aTmp = aTmp.replace('.', rParam.cDecSep); 2515 2516 if (rString.getLength()) 2517 rString.appendAscii(" "); 2518 rString.append(aTmp); 2519 2520 } break; 2521 case SQL_NODE_PUNCTUATION: 2522 if ( getParent() && SQL_ISRULE(getParent(),cast_spec) && m_aNodeValue.toChar() == '(' ) // no spaces in front of '(' 2523 { 2524 rString.append(m_aNodeValue); 2525 break; 2526 } 2527 // fall through 2528 default: 2529 if (rString.getLength() && m_aNodeValue.toChar() != '.' && m_aNodeValue.toChar() != ':' ) 2530 { 2531 switch( rString.charAt(rString.getLength()-1) ) 2532 { 2533 case ' ' : 2534 case '.' : break; 2535 default : 2536 if ( !rParam.aMetaData.getCatalogSeparator().getLength() 2537 || rString.charAt( rString.getLength()-1 ) != rParam.aMetaData.getCatalogSeparator().toChar() 2538 ) 2539 rString.appendAscii(" "); break; 2540 } 2541 } 2542 rString.append(m_aNodeValue); 2543 } 2544 } 2545 2546 // ----------------------------------------------------------------------------- 2547 sal_Int32 OSQLParser::getFunctionReturnType(const ::rtl::OUString& _sFunctionName, const IParseContext* pContext) 2548 { 2549 sal_Int32 nType = DataType::VARCHAR; 2550 ::rtl::OString sFunctionName( rtl::OUStringToOString( _sFunctionName, RTL_TEXTENCODING_UTF8)); 2551 2552 if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_ASCII,pContext))) nType = DataType::INTEGER; 2553 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_BIT_LENGTH,pContext))) nType = DataType::INTEGER; 2554 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_CHAR,pContext))) nType = DataType::VARCHAR; 2555 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_CHAR_LENGTH,pContext))) nType = DataType::INTEGER; 2556 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_CONCAT,pContext))) nType = DataType::VARCHAR; 2557 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_DIFFERENCE,pContext))) nType = DataType::VARCHAR; 2558 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_INSERT,pContext))) nType = DataType::VARCHAR; 2559 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_LCASE,pContext))) nType = DataType::VARCHAR; 2560 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_LEFT,pContext))) nType = DataType::VARCHAR; 2561 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_LENGTH,pContext))) nType = DataType::INTEGER; 2562 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_LOCATE,pContext))) nType = DataType::VARCHAR; 2563 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_LOCATE_2,pContext))) nType = DataType::VARCHAR; 2564 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_LTRIM,pContext))) nType = DataType::VARCHAR; 2565 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_OCTET_LENGTH,pContext))) nType = DataType::INTEGER; 2566 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_POSITION,pContext))) nType = DataType::INTEGER; 2567 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_REPEAT,pContext))) nType = DataType::VARCHAR; 2568 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_REPLACE,pContext))) nType = DataType::VARCHAR; 2569 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_RIGHT,pContext))) nType = DataType::VARCHAR; 2570 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_RTRIM,pContext))) nType = DataType::VARCHAR; 2571 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_SOUNDEX,pContext))) nType = DataType::VARCHAR; 2572 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_SPACE,pContext))) nType = DataType::VARCHAR; 2573 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_SUBSTRING,pContext))) nType = DataType::VARCHAR; 2574 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_UCASE,pContext))) nType = DataType::VARCHAR; 2575 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_CURRENT_DATE,pContext))) nType = DataType::DATE; 2576 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_CURRENT_TIME,pContext))) nType = DataType::TIME; 2577 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_CURRENT_TIMESTAMP,pContext))) nType = DataType::TIMESTAMP; 2578 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_CURDATE,pContext))) nType = DataType::DATE; 2579 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_DATEDIFF,pContext))) nType = DataType::INTEGER; 2580 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_DATEVALUE,pContext))) nType = DataType::DATE; 2581 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_CURTIME,pContext))) nType = DataType::TIME; 2582 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_DAYNAME,pContext))) nType = DataType::VARCHAR; 2583 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_DAYOFMONTH,pContext))) nType = DataType::INTEGER; 2584 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_DAYOFWEEK,pContext))) nType = DataType::INTEGER; 2585 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_DAYOFYEAR,pContext))) nType = DataType::INTEGER; 2586 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_EXTRACT,pContext))) nType = DataType::VARCHAR; 2587 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_HOUR,pContext))) nType = DataType::INTEGER; 2588 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_MINUTE,pContext))) nType = DataType::INTEGER; 2589 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_MONTH,pContext))) nType = DataType::INTEGER; 2590 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_MONTHNAME,pContext))) nType = DataType::VARCHAR; 2591 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_NOW,pContext))) nType = DataType::TIMESTAMP; 2592 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_QUARTER,pContext))) nType = DataType::INTEGER; 2593 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_SECOND,pContext))) nType = DataType::INTEGER; 2594 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_TIMESTAMPADD,pContext))) nType = DataType::TIMESTAMP; 2595 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_TIMESTAMPDIFF,pContext))) nType = DataType::TIMESTAMP; 2596 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_TIMEVALUE,pContext))) nType = DataType::TIMESTAMP; 2597 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_WEEK,pContext))) nType = DataType::INTEGER; 2598 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_YEAR,pContext))) nType = DataType::INTEGER; 2599 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_ABS,pContext))) nType = DataType::DOUBLE; 2600 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_ACOS,pContext))) nType = DataType::DOUBLE; 2601 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_ASIN,pContext))) nType = DataType::DOUBLE; 2602 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_ATAN,pContext))) nType = DataType::DOUBLE; 2603 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_ATAN2,pContext))) nType = DataType::DOUBLE; 2604 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_CEILING,pContext))) nType = DataType::DOUBLE; 2605 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_COS,pContext))) nType = DataType::DOUBLE; 2606 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_COT,pContext))) nType = DataType::DOUBLE; 2607 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_DEGREES,pContext))) nType = DataType::DOUBLE; 2608 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_EXP,pContext))) nType = DataType::DOUBLE; 2609 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_FLOOR,pContext))) nType = DataType::DOUBLE; 2610 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_LOGF,pContext))) nType = DataType::DOUBLE; 2611 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_LOG,pContext))) nType = DataType::DOUBLE; 2612 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_LOG10,pContext))) nType = DataType::DOUBLE; 2613 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_LN,pContext))) nType = DataType::DOUBLE; 2614 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_MOD,pContext))) nType = DataType::DOUBLE; 2615 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_PI,pContext))) nType = DataType::DOUBLE; 2616 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_POWER,pContext))) nType = DataType::DOUBLE; 2617 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_RADIANS,pContext))) nType = DataType::DOUBLE; 2618 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_RAND,pContext))) nType = DataType::DOUBLE; 2619 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_ROUND,pContext))) nType = DataType::DOUBLE; 2620 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_ROUNDMAGIC,pContext))) nType = DataType::DOUBLE; 2621 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_SIGN,pContext))) nType = DataType::DOUBLE; 2622 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_SIN,pContext))) nType = DataType::DOUBLE; 2623 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_SQRT,pContext))) nType = DataType::DOUBLE; 2624 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_TAN,pContext))) nType = DataType::DOUBLE; 2625 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_TRUNCATE,pContext))) nType = DataType::DOUBLE; 2626 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_COUNT,pContext))) nType = DataType::INTEGER; 2627 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_MAX,pContext))) nType = DataType::DOUBLE; 2628 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_MIN,pContext))) nType = DataType::DOUBLE; 2629 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_AVG,pContext))) nType = DataType::DOUBLE; 2630 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_SUM,pContext))) nType = DataType::DOUBLE; 2631 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_LOWER,pContext))) nType = DataType::VARCHAR; 2632 else if(sFunctionName.equalsIgnoreAsciiCase(TokenIDToStr(SQL_TOKEN_UPPER,pContext))) nType = DataType::VARCHAR; 2633 2634 return nType; 2635 } 2636 // ----------------------------------------------------------------------------- 2637 sal_Int32 OSQLParser::getFunctionParameterType(sal_uInt32 _nTokenId, sal_uInt32 _nPos) 2638 { 2639 sal_Int32 nType = DataType::VARCHAR; 2640 2641 if(_nTokenId == SQL_TOKEN_CHAR) nType = DataType::INTEGER; 2642 else if(_nTokenId == SQL_TOKEN_INSERT) 2643 { 2644 if ( _nPos == 2 || _nPos == 3 ) 2645 nType = DataType::INTEGER; 2646 } 2647 else if(_nTokenId == SQL_TOKEN_LEFT) 2648 { 2649 if ( _nPos == 2 ) 2650 nType = DataType::INTEGER; 2651 } 2652 else if(_nTokenId == SQL_TOKEN_LOCATE) 2653 { 2654 if ( _nPos == 3 ) 2655 nType = DataType::INTEGER; 2656 } 2657 else if(_nTokenId == SQL_TOKEN_LOCATE_2) 2658 { 2659 if ( _nPos == 3 ) 2660 nType = DataType::INTEGER; 2661 } 2662 else if( _nTokenId == SQL_TOKEN_REPEAT || _nTokenId == SQL_TOKEN_RIGHT ) 2663 { 2664 if ( _nPos == 2 ) 2665 nType = DataType::INTEGER; 2666 } 2667 else if(_nTokenId == SQL_TOKEN_SPACE ) 2668 { 2669 nType = DataType::INTEGER; 2670 } 2671 else if(_nTokenId == SQL_TOKEN_SUBSTRING) 2672 { 2673 if ( _nPos != 1 ) 2674 nType = DataType::INTEGER; 2675 } 2676 else if(_nTokenId == SQL_TOKEN_DATEDIFF) 2677 { 2678 if ( _nPos != 1 ) 2679 nType = DataType::TIMESTAMP; 2680 } 2681 else if(_nTokenId == SQL_TOKEN_DATEVALUE) 2682 nType = DataType::DATE; 2683 else if(_nTokenId == SQL_TOKEN_DAYNAME) 2684 nType = DataType::DATE; 2685 else if(_nTokenId == SQL_TOKEN_DAYOFMONTH) 2686 nType = DataType::DATE; 2687 else if(_nTokenId == SQL_TOKEN_DAYOFWEEK) 2688 nType = DataType::DATE; 2689 else if(_nTokenId == SQL_TOKEN_DAYOFYEAR) 2690 nType = DataType::DATE; 2691 else if(_nTokenId == SQL_TOKEN_EXTRACT) nType = DataType::VARCHAR; 2692 else if(_nTokenId == SQL_TOKEN_HOUR) nType = DataType::TIME; 2693 else if(_nTokenId == SQL_TOKEN_MINUTE) nType = DataType::TIME; 2694 else if(_nTokenId == SQL_TOKEN_MONTH) nType = DataType::DATE; 2695 else if(_nTokenId == SQL_TOKEN_MONTHNAME) nType = DataType::DATE; 2696 else if(_nTokenId == SQL_TOKEN_NOW) nType = DataType::TIMESTAMP; 2697 else if(_nTokenId == SQL_TOKEN_QUARTER) nType = DataType::DATE; 2698 else if(_nTokenId == SQL_TOKEN_SECOND) nType = DataType::TIME; 2699 else if(_nTokenId == SQL_TOKEN_TIMESTAMPADD) nType = DataType::TIMESTAMP; 2700 else if(_nTokenId == SQL_TOKEN_TIMESTAMPDIFF) nType = DataType::TIMESTAMP; 2701 else if(_nTokenId == SQL_TOKEN_TIMEVALUE) nType = DataType::TIMESTAMP; 2702 else if(_nTokenId == SQL_TOKEN_WEEK) nType = DataType::DATE; 2703 else if(_nTokenId == SQL_TOKEN_YEAR) nType = DataType::DATE; 2704 2705 else if(_nTokenId == SQL_TOKEN_ABS) nType = DataType::DOUBLE; 2706 else if(_nTokenId == SQL_TOKEN_ACOS) nType = DataType::DOUBLE; 2707 else if(_nTokenId == SQL_TOKEN_ASIN) nType = DataType::DOUBLE; 2708 else if(_nTokenId == SQL_TOKEN_ATAN) nType = DataType::DOUBLE; 2709 else if(_nTokenId == SQL_TOKEN_ATAN2) nType = DataType::DOUBLE; 2710 else if(_nTokenId == SQL_TOKEN_CEILING) nType = DataType::DOUBLE; 2711 else if(_nTokenId == SQL_TOKEN_COS) nType = DataType::DOUBLE; 2712 else if(_nTokenId == SQL_TOKEN_COT) nType = DataType::DOUBLE; 2713 else if(_nTokenId == SQL_TOKEN_DEGREES) nType = DataType::DOUBLE; 2714 else if(_nTokenId == SQL_TOKEN_EXP) nType = DataType::DOUBLE; 2715 else if(_nTokenId == SQL_TOKEN_FLOOR) nType = DataType::DOUBLE; 2716 else if(_nTokenId == SQL_TOKEN_LOGF) nType = DataType::DOUBLE; 2717 else if(_nTokenId == SQL_TOKEN_LOG) nType = DataType::DOUBLE; 2718 else if(_nTokenId == SQL_TOKEN_LOG10) nType = DataType::DOUBLE; 2719 else if(_nTokenId == SQL_TOKEN_LN) nType = DataType::DOUBLE; 2720 else if(_nTokenId == SQL_TOKEN_MOD) nType = DataType::DOUBLE; 2721 else if(_nTokenId == SQL_TOKEN_PI) nType = DataType::DOUBLE; 2722 else if(_nTokenId == SQL_TOKEN_POWER) nType = DataType::DOUBLE; 2723 else if(_nTokenId == SQL_TOKEN_RADIANS) nType = DataType::DOUBLE; 2724 else if(_nTokenId == SQL_TOKEN_RAND) nType = DataType::DOUBLE; 2725 else if(_nTokenId == SQL_TOKEN_ROUND) nType = DataType::DOUBLE; 2726 else if(_nTokenId == SQL_TOKEN_ROUNDMAGIC) nType = DataType::DOUBLE; 2727 else if(_nTokenId == SQL_TOKEN_SIGN) nType = DataType::DOUBLE; 2728 else if(_nTokenId == SQL_TOKEN_SIN) nType = DataType::DOUBLE; 2729 else if(_nTokenId == SQL_TOKEN_SQRT) nType = DataType::DOUBLE; 2730 else if(_nTokenId == SQL_TOKEN_TAN) nType = DataType::DOUBLE; 2731 else if(_nTokenId == SQL_TOKEN_TRUNCATE) nType = DataType::DOUBLE; 2732 else if(_nTokenId == SQL_TOKEN_COUNT) nType = DataType::INTEGER; 2733 else if(_nTokenId == SQL_TOKEN_MAX) nType = DataType::DOUBLE; 2734 else if(_nTokenId == SQL_TOKEN_MIN) nType = DataType::DOUBLE; 2735 else if(_nTokenId == SQL_TOKEN_AVG) nType = DataType::DOUBLE; 2736 else if(_nTokenId == SQL_TOKEN_SUM) nType = DataType::DOUBLE; 2737 2738 else if(_nTokenId == SQL_TOKEN_LOWER) nType = DataType::VARCHAR; 2739 else if(_nTokenId == SQL_TOKEN_UPPER) nType = DataType::VARCHAR; 2740 2741 return nType; 2742 } 2743 2744 // ----------------------------------------------------------------------------- 2745 const SQLError& OSQLParser::getErrorHelper() const 2746 { 2747 return m_pData->aErrors; 2748 } 2749 2750 // ----------------------------------------------------------------------------- 2751 OSQLParseNode::Rule OSQLParseNode::getKnownRuleID() const 2752 { 2753 if ( !isRule() ) 2754 return UNKNOWN_RULE; 2755 return OSQLParser::RuleIDToRule( getRuleID() ); 2756 } 2757 // ----------------------------------------------------------------------------- 2758 ::rtl::OUString OSQLParseNode::getTableRange(const OSQLParseNode* _pTableRef) 2759 { 2760 RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "parse", "Ocke.Janssen@sun.com", "OSQLParseNode::getTableRange" ); 2761 OSL_ENSURE(_pTableRef && _pTableRef->count() > 1 && _pTableRef->getKnownRuleID() == OSQLParseNode::table_ref,"Invalid node give, only table ref is allowed!"); 2762 const sal_uInt32 nCount = _pTableRef->count(); 2763 ::rtl::OUString sTableRange; 2764 if ( nCount == 2 || (nCount == 3 && !_pTableRef->getChild(0)->isToken()) || nCount == 5 ) 2765 { 2766 const OSQLParseNode* pNode = _pTableRef->getChild(nCount - (nCount == 2 ? 1 : 2)); 2767 OSL_ENSURE(pNode && (pNode->getKnownRuleID() == OSQLParseNode::table_primary_as_range_column 2768 || pNode->getKnownRuleID() == OSQLParseNode::range_variable) 2769 ,"SQL grammar changed!"); 2770 if ( !pNode->isLeaf() ) 2771 sTableRange = pNode->getChild(1)->getTokenValue(); 2772 } // if ( nCount == 2 || nCount == 3 || nCount == 5) 2773 2774 return sTableRange; 2775 } 2776 // ----------------------------------------------------------------------------- 2777 OSQLParseNodesContainer::OSQLParseNodesContainer() 2778 { 2779 } 2780 // ----------------------------------------------------------------------------- 2781 OSQLParseNodesContainer::~OSQLParseNodesContainer() 2782 { 2783 } 2784 // ----------------------------------------------------------------------------- 2785 void OSQLParseNodesContainer::push_back(OSQLParseNode* _pNode) 2786 { 2787 ::osl::MutexGuard aGuard(m_aMutex); 2788 m_aNodes.push_back(_pNode); 2789 } 2790 // ----------------------------------------------------------------------------- 2791 void OSQLParseNodesContainer::erase(OSQLParseNode* _pNode) 2792 { 2793 ::osl::MutexGuard aGuard(m_aMutex); 2794 if ( !m_aNodes.empty() ) 2795 { 2796 ::std::vector< OSQLParseNode* >::iterator aFind = ::std::find(m_aNodes.begin(), m_aNodes.end(),_pNode); 2797 if ( aFind != m_aNodes.end() ) 2798 m_aNodes.erase(aFind); 2799 } 2800 } 2801 // ----------------------------------------------------------------------------- 2802 bool OSQLParseNodesContainer::empty() const 2803 { 2804 return m_aNodes.empty(); 2805 } 2806 // ----------------------------------------------------------------------------- 2807 void OSQLParseNodesContainer::clear() 2808 { 2809 ::osl::MutexGuard aGuard(m_aMutex); 2810 m_aNodes.clear(); 2811 } 2812 // ----------------------------------------------------------------------------- 2813 void OSQLParseNodesContainer::clearAndDelete() 2814 { 2815 ::osl::MutexGuard aGuard(m_aMutex); 2816 // clear the garbage collector 2817 while ( !m_aNodes.empty() ) 2818 { 2819 OSQLParseNode* pNode = m_aNodes[0]; 2820 while ( pNode->getParent() ) 2821 { 2822 pNode = pNode->getParent(); 2823 } 2824 delete pNode; 2825 } 2826 } 2827 } // namespace connectivity 2828