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 // MARKER(update_precomp.py): autogen include statement, do not remove 23 #include "precompiled_ucb.hxx" 24 25 #include <hash_map> 26 #include <vector> 27 #include <string.h> 28 #include <rtl/string.h> 29 #include "comphelper/sequence.hxx" 30 #include "ucbhelper/simplecertificatevalidationrequest.hxx" 31 32 #include <AprEnv.hxx> 33 #include <apr_strings.h> 34 35 #include "DAVAuthListener.hxx" 36 #include <SerfTypes.hxx> 37 #include <SerfSession.hxx> 38 #include <SerfUri.hxx> 39 #include <SerfRequestProcessor.hxx> 40 #include <SerfCallbacks.hxx> 41 #include <SerfInputStream.hxx> 42 #include <UCBDeadPropertyValue.hxx> 43 44 #include <com/sun/star/xml/crypto/XSecurityEnvironment.hpp> 45 #include <com/sun/star/security/XCertificate.hpp> 46 #include <com/sun/star/security/CertificateValidity.hpp> 47 #include <com/sun/star/security/CertificateContainerStatus.hpp> 48 #include <com/sun/star/security/CertificateContainer.hpp> 49 #include <com/sun/star/security/XCertificateContainer.hpp> 50 #include <com/sun/star/ucb/Lock.hpp> 51 #include <com/sun/star/xml/crypto/XSEInitializer.hpp> 52 53 using namespace com::sun::star; 54 using namespace http_dav_ucp; 55 56 // ------------------------------------------------------------------- 57 // static members! 58 bool SerfSession::m_bGlobalsInited = false; 59 osl::Mutex SerfSession::m_aGlobalMutex; 60 //SerfLockStore SerfSession::m_aSerfLockStore; 61 62 // ------------------------------------------------------------------- 63 // Constructor 64 // ------------------------------------------------------------------- 65 SerfSession::SerfSession( 66 const rtl::Reference< DAVSessionFactory > & rSessionFactory, 67 const rtl::OUString& inUri, 68 const ucbhelper::InternetProxyDecider & rProxyDecider ) 69 throw ( DAVException ) 70 : DAVSession( rSessionFactory ) 71 , m_aMutex() 72 , m_aUri( inUri ) 73 , m_aProxyName() 74 , m_nProxyPort( 0 ) 75 , m_pSerfConnection( 0 ) 76 , m_pSerfContext( 0 ) 77 , m_bIsHeadRequestInProgress( false ) 78 , m_rProxyDecider( rProxyDecider ) 79 , m_aEnv() 80 { 81 m_pSerfContext = serf_context_create( getAprPool() ); 82 83 m_pSerfBucket_Alloc = serf_bucket_allocator_create( getAprPool(), NULL, NULL ); 84 } 85 86 // ------------------------------------------------------------------- 87 // Destructor 88 // ------------------------------------------------------------------- 89 SerfSession::~SerfSession( ) 90 { 91 if ( m_pSerfConnection ) 92 { 93 serf_connection_close( m_pSerfConnection ); 94 m_pSerfConnection = 0; 95 } 96 } 97 98 // ------------------------------------------------------------------- 99 void SerfSession::Init( const DAVRequestEnvironment & rEnv ) 100 throw ( DAVException ) 101 { 102 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 103 m_aEnv = rEnv; 104 Init(); 105 } 106 107 // ------------------------------------------------------------------- 108 void SerfSession::Init() 109 throw ( DAVException ) 110 { 111 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 112 113 bool bCreateNewSession = false; 114 115 if ( m_pSerfConnection == 0 ) 116 { 117 osl::Guard< osl::Mutex > theGlobalGuard( m_aGlobalMutex ); 118 // <-- 119 if ( !m_bGlobalsInited ) 120 { 121 // TODO - figure out, if anything has to be done here 122 m_bGlobalsInited = true; 123 } 124 125 const ucbhelper::InternetProxyServer & rProxyCfg = getProxySettings(); 126 127 m_aProxyName = rProxyCfg.aName; 128 m_nProxyPort = rProxyCfg.nPort; 129 130 // Not yet initialized. Create new session. 131 bCreateNewSession = true; 132 } 133 else 134 { 135 const ucbhelper::InternetProxyServer & rProxyCfg = getProxySettings(); 136 137 if ( ( rProxyCfg.aName != m_aProxyName ) 138 || ( rProxyCfg.nPort != m_nProxyPort ) ) 139 { 140 m_aProxyName = rProxyCfg.aName; 141 m_nProxyPort = rProxyCfg.nPort; 142 143 // new session needed, destroy old first 144 serf_connection_close( m_pSerfConnection ); 145 m_pSerfConnection = 0; 146 bCreateNewSession = true; 147 } 148 } 149 150 if ( bCreateNewSession ) 151 { 152 // TODO - close_connection callback 153 apr_status_t status = serf_connection_create2( &m_pSerfConnection, 154 m_pSerfContext, 155 *(m_aUri.getAprUri()), 156 Serf_ConnectSetup, this, 157 0 /* close connection callback */, 0 /* close connection baton */, 158 getAprPool() ); 159 160 if ( m_pSerfConnection == 0 ||status != APR_SUCCESS ) 161 { 162 throw DAVException( DAVException::DAV_SESSION_CREATE, 163 SerfUri::makeConnectionEndPointString( m_aUri.GetHost(), m_aUri.GetPort() ) ); 164 } 165 166 // Register the session with the lock store 167 // m_aSerfLockStore.registerSession( m_pSerfConnection ); 168 169 if ( m_aProxyName.getLength() ) 170 { 171 apr_sockaddr_t *proxy_address = NULL; 172 const apr_status_t status = apr_sockaddr_info_get( &proxy_address, 173 rtl::OUStringToOString( m_aProxyName, RTL_TEXTENCODING_UTF8 ), 174 APR_UNSPEC, 175 static_cast<apr_port_t>(m_nProxyPort), 176 0, getAprPool() ); 177 178 if ( status != APR_SUCCESS ) 179 { 180 throw DAVException( DAVException::DAV_SESSION_CREATE, 181 SerfUri::makeConnectionEndPointString( m_aUri.GetHost(), m_aUri.GetPort() ) ); 182 } 183 184 serf_config_proxy( m_pSerfContext, proxy_address ); 185 } 186 187 188 serf_config_credentials_callback( m_pSerfContext, Serf_Credentials ); 189 } 190 } 191 192 apr_pool_t* SerfSession::getAprPool() 193 { 194 return apr_environment::AprEnv::getAprEnv()->getAprPool(); 195 } 196 197 serf_bucket_alloc_t* SerfSession::getSerfBktAlloc() 198 { 199 return m_pSerfBucket_Alloc; 200 } 201 202 serf_context_t* SerfSession::getSerfContext() 203 { 204 return m_pSerfContext; 205 } 206 207 SerfConnection* SerfSession::getSerfConnection() 208 { 209 return m_pSerfConnection; 210 } 211 212 bool SerfSession::isHeadRequestInProgress() 213 { 214 return m_bIsHeadRequestInProgress; 215 } 216 217 bool SerfSession::isSSLNeeded() 218 { 219 return m_aUri.GetScheme().equalsIgnoreAsciiCase( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "https" ) ) ); 220 } 221 222 char* SerfSession::getHostinfo() 223 { 224 return m_aUri.getAprUri()->hostinfo; 225 } 226 227 228 // ------------------------------------------------------------------- 229 // virtual 230 sal_Bool SerfSession::CanUse( const rtl::OUString & inUri ) 231 { 232 try 233 { 234 SerfUri theUri( inUri ); 235 if ( ( theUri.GetPort() == m_aUri.GetPort() ) && 236 ( theUri.GetHost() == m_aUri.GetHost() ) && 237 ( theUri.GetScheme() == m_aUri.GetScheme() ) ) 238 { 239 return sal_True; 240 } 241 } 242 catch ( DAVException const & ) 243 { 244 return sal_False; 245 } 246 return sal_False; 247 } 248 249 // ------------------------------------------------------------------- 250 // virtual 251 sal_Bool SerfSession::UsesProxy() 252 { 253 Init(); 254 return ( m_aProxyName.getLength() > 0 ); 255 } 256 257 apr_status_t SerfSession::setupSerfConnection( apr_socket_t * inAprSocket, 258 serf_bucket_t **outSerfInputBucket, 259 serf_bucket_t **outSerfOutputBucket, 260 apr_pool_t* /*inAprPool*/ ) 261 { 262 serf_bucket_t *tmpInputBkt; 263 tmpInputBkt = serf_context_bucket_socket_create( getSerfContext(), 264 inAprSocket, 265 getSerfBktAlloc() ); 266 267 if ( isSSLNeeded() ) 268 { 269 tmpInputBkt = serf_bucket_ssl_decrypt_create( tmpInputBkt, 270 0, 271 getSerfBktAlloc() ); 272 serf_ssl_server_cert_callback_set( serf_bucket_ssl_decrypt_context_get( tmpInputBkt ), 273 Serf_CertificationValidation, 274 this ); 275 serf_ssl_set_hostname( serf_bucket_ssl_decrypt_context_get( tmpInputBkt ), 276 getHostinfo() ); 277 278 *outSerfOutputBucket = serf_bucket_ssl_encrypt_create( *outSerfOutputBucket, 279 serf_bucket_ssl_decrypt_context_get( tmpInputBkt ), 280 getSerfBktAlloc() ); 281 } 282 283 *outSerfInputBucket = tmpInputBkt; 284 285 return APR_SUCCESS; 286 } 287 288 apr_status_t SerfSession::provideSerfCredentials( bool bGiveProvidedCredentialsASecondTry, 289 char ** outUsername, 290 char ** outPassword, 291 serf_request_t * /*inRequest*/, 292 int /*inCode*/, 293 const char *inAuthProtocol, 294 const char *inRealm, 295 apr_pool_t *inAprPool ) 296 { 297 DAVAuthListener * pListener = getRequestEnvironment().m_xAuthListener.get(); 298 if ( !pListener ) 299 { 300 // abort 301 return SERF_ERROR_AUTHN_FAILED; 302 } 303 304 rtl::OUString theUserName; 305 rtl::OUString thePassWord; 306 try 307 { 308 SerfUri uri( getRequestEnvironment().m_aRequestURI ); 309 rtl::OUString aUserInfo( uri.GetUserInfo() ); 310 if ( aUserInfo.getLength() ) 311 { 312 sal_Int32 nPos = aUserInfo.indexOf( '@' ); 313 if ( nPos == -1 ) 314 { 315 theUserName = aUserInfo; 316 } 317 else 318 { 319 theUserName = aUserInfo.copy( 0, nPos ); 320 thePassWord = aUserInfo.copy( nPos + 1 ); 321 } 322 } 323 } 324 catch ( DAVException const & ) 325 { 326 // abort 327 return SERF_ERROR_AUTHN_FAILED; 328 } 329 330 const bool bCanUseSystemCreds = ( ( strcasecmp( inAuthProtocol, "NTLM" ) == 0 ) || 331 ( strcasecmp( inAuthProtocol, "Negotiate" ) == 0 ) ); 332 333 int theRetVal = pListener->authenticate( rtl::OUString::createFromAscii( inRealm ), 334 getHostName(), 335 theUserName, 336 thePassWord, 337 bCanUseSystemCreds, 338 bGiveProvidedCredentialsASecondTry ? sal_False : sal_True ); 339 340 if ( theRetVal == 0 ) 341 { 342 *outUsername = apr_pstrdup( inAprPool, rtl::OUStringToOString( theUserName, RTL_TEXTENCODING_UTF8 ) ); 343 *outPassword = apr_pstrdup( inAprPool, rtl::OUStringToOString( thePassWord, RTL_TEXTENCODING_UTF8 ) ); 344 } 345 346 return theRetVal != 0 ? SERF_ERROR_AUTHN_FAILED : APR_SUCCESS; 347 } 348 349 namespace { 350 // ------------------------------------------------------------------- 351 // Helper function 352 ::rtl::OUString GetHostnamePart( const ::rtl::OUString& _rRawString ) 353 { 354 ::rtl::OUString sPart; 355 ::rtl::OUString sPartId = ::rtl::OUString::createFromAscii( "CN=" ); 356 sal_Int32 nContStart = _rRawString.indexOf( sPartId ); 357 if ( nContStart != -1 ) 358 { 359 nContStart = nContStart + sPartId.getLength(); 360 sal_Int32 nContEnd 361 = _rRawString.indexOf( sal_Unicode( ',' ), nContStart ); 362 sPart = _rRawString.copy( nContStart, nContEnd - nContStart ); 363 } 364 return sPart; 365 } 366 } // namespace 367 368 apr_status_t SerfSession::verifySerfCertificate( int inFailures, 369 const serf_ssl_certificate_t * inCert ) 370 { 371 OSL_ASSERT( inCert ); 372 373 uno::Reference< security::XCertificateContainer > xCertificateContainer; 374 try 375 { 376 xCertificateContainer 377 = uno::Reference< security::XCertificateContainer >( 378 getMSF()->createInstance( 379 rtl::OUString::createFromAscii( 380 "com.sun.star.security.CertificateContainer" ) ), 381 uno::UNO_QUERY ); 382 } 383 catch ( uno::Exception const & ) 384 { 385 } 386 387 if ( !xCertificateContainer.is() ) 388 return SERF_SSL_CERT_UNKNOWN_FAILURE; 389 390 inFailures = 0; 391 392 const char * subjectItem = static_cast<char*>(apr_hash_get( serf_ssl_cert_subject( inCert, getAprPool() ), 393 "CN", APR_HASH_KEY_STRING )); 394 if ( subjectItem == 0 ) 395 { 396 subjectItem = static_cast<char*>(apr_hash_get( serf_ssl_cert_subject( inCert, getAprPool() ), 397 "OU", APR_HASH_KEY_STRING )); 398 } 399 rtl::OUString cert_subject; 400 if ( subjectItem != 0 ) 401 { 402 cert_subject = rtl::OUString( subjectItem, strlen( subjectItem ), RTL_TEXTENCODING_UTF8, 0 ); 403 } 404 else 405 { 406 rtl::OUString::createFromAscii( "unknown subject" ); 407 } 408 409 security::CertificateContainerStatus certificateContainer( 410 xCertificateContainer->hasCertificate( 411 getHostName(), cert_subject ) ); 412 413 if ( certificateContainer != security::CertificateContainerStatus_NOCERT ) 414 { 415 return certificateContainer == security::CertificateContainerStatus_TRUSTED 416 ? APR_SUCCESS 417 : SERF_SSL_CERT_UNKNOWN_FAILURE; 418 } 419 420 uno::Reference< xml::crypto::XSEInitializer > xSEInitializer; 421 try 422 { 423 xSEInitializer = uno::Reference< xml::crypto::XSEInitializer >( 424 getMSF()->createInstance( 425 rtl::OUString::createFromAscii( "com.sun.star.xml.crypto.SEInitializer" ) ), 426 uno::UNO_QUERY ); 427 } 428 catch ( uno::Exception const & ) 429 { 430 } 431 432 if ( !xSEInitializer.is() ) 433 return SERF_SSL_CERT_UNKNOWN_FAILURE; 434 435 uno::Reference< xml::crypto::XXMLSecurityContext > xSecurityContext( 436 xSEInitializer->createSecurityContext( rtl::OUString() ) ); 437 438 uno::Reference< xml::crypto::XSecurityEnvironment > xSecurityEnv( 439 xSecurityContext->getSecurityEnvironment() ); 440 441 //The end entity certificate 442 const char * eeCertB64 = serf_ssl_cert_export( inCert, getAprPool() ); 443 444 rtl::OString sEECertB64( eeCertB64 ); 445 446 uno::Reference< security::XCertificate > xEECert( 447 xSecurityEnv->createCertificateFromAscii( 448 rtl::OStringToOUString( sEECertB64, RTL_TEXTENCODING_ASCII_US ) ) ); 449 450 std::vector< uno::Reference< security::XCertificate > > vecCerts; 451 const serf_ssl_certificate_t * issuerCert = inCert; 452 do 453 { 454 //get the intermediate certificate 455 issuerCert = NULL; // TODO - figure out how to retrieve certificate chain - ssl_cert_signedby( issuerCert ); 456 if ( NULL == issuerCert ) 457 break; 458 459 const char * imCertB64 = serf_ssl_cert_export( issuerCert, getAprPool() ); 460 rtl::OString sInterMediateCertB64( imCertB64 ); 461 462 uno::Reference< security::XCertificate> xImCert( 463 xSecurityEnv->createCertificateFromAscii( 464 rtl::OStringToOUString( 465 sInterMediateCertB64, RTL_TEXTENCODING_ASCII_US ) ) ); 466 if ( xImCert.is() ) 467 vecCerts.push_back( xImCert ); 468 } 469 while ( 1 ); 470 471 sal_Int64 certValidity = xSecurityEnv->verifyCertificate( xEECert, 472 ::comphelper::containerToSequence( vecCerts ) ); 473 474 if ( isDomainMatch( GetHostnamePart( xEECert.get()->getSubjectName() ) ) ) 475 { 476 // if host name matched with certificate then look if the 477 // certificate was ok 478 if( certValidity == security::CertificateValidity::VALID ) 479 return APR_SUCCESS; 480 } 481 482 const uno::Reference< ucb::XCommandEnvironment > xEnv( getRequestEnvironment().m_xEnv ); 483 if ( xEnv.is() ) 484 { 485 inFailures = static_cast< int >( certValidity ); 486 487 uno::Reference< task::XInteractionHandler > xIH( xEnv->getInteractionHandler() ); 488 if ( xIH.is() ) 489 { 490 rtl::Reference< ucbhelper::SimpleCertificateValidationRequest > 491 xRequest( new ucbhelper::SimpleCertificateValidationRequest( 492 (sal_Int32)inFailures, xEECert, getHostName() ) ); 493 xIH->handle( xRequest.get() ); 494 495 rtl::Reference< ucbhelper::InteractionContinuation > xSelection 496 = xRequest->getSelection(); 497 498 if ( xSelection.is() ) 499 { 500 uno::Reference< task::XInteractionApprove > xApprove( 501 xSelection.get(), uno::UNO_QUERY ); 502 if ( xApprove.is() ) 503 { 504 xCertificateContainer->addCertificate( getHostName(), cert_subject, sal_True ); 505 return APR_SUCCESS; 506 } 507 else 508 { 509 // Don't trust cert 510 xCertificateContainer->addCertificate( getHostName(), cert_subject, sal_False ); 511 return SERF_SSL_CERT_UNKNOWN_FAILURE; 512 } 513 } 514 } 515 else 516 { 517 // Don't trust cert 518 xCertificateContainer->addCertificate( getHostName(), cert_subject, sal_False ); 519 return SERF_SSL_CERT_UNKNOWN_FAILURE; 520 } 521 } 522 return SERF_SSL_CERT_UNKNOWN_FAILURE; 523 } 524 525 serf_bucket_t* SerfSession::acceptSerfResponse( serf_request_t * inSerfRequest, 526 serf_bucket_t * inSerfStreamBucket, 527 apr_pool_t* /*inAprPool*/ ) 528 { 529 // get the per-request bucket allocator 530 serf_bucket_alloc_t* SerfBktAlloc = serf_request_get_alloc( inSerfRequest ); 531 532 // create a barrier bucket so the response doesn't eat us! 533 serf_bucket_t *responseBkt = serf_bucket_barrier_create( inSerfStreamBucket, 534 SerfBktAlloc ); 535 536 // create response bucket 537 responseBkt = serf_bucket_response_create( responseBkt, 538 SerfBktAlloc ); 539 540 if ( isHeadRequestInProgress() ) 541 { 542 // advise the response bucket that this was from a HEAD request and that it should not expect to see a response body. 543 serf_bucket_response_set_head( responseBkt ); 544 } 545 546 return responseBkt; 547 } 548 549 // ------------------------------------------------------------------- 550 // PROPFIND - allprop & named 551 // ------------------------------------------------------------------- 552 void SerfSession::PROPFIND( const rtl::OUString & inPath, 553 const Depth inDepth, 554 const std::vector< rtl::OUString > & inPropNames, 555 std::vector< DAVResource > & ioResources, 556 const DAVRequestEnvironment & rEnv ) 557 throw ( DAVException ) 558 { 559 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 560 561 Init( rEnv ); 562 563 apr_status_t status = APR_SUCCESS; 564 SerfRequestProcessor aReqProc( *this, 565 inPath ); 566 aReqProc.processPropFind( inDepth, 567 inPropNames, 568 ioResources, 569 status ); 570 571 if ( status == APR_SUCCESS && 572 aReqProc.mpDAVException == 0 && 573 ioResources.empty() ) 574 { 575 m_aEnv = DAVRequestEnvironment(); 576 throw DAVException( DAVException::DAV_HTTP_ERROR, inPath, (sal_uInt16)APR_EGENERAL ); 577 } 578 HandleError( aReqProc, 579 inPath, rEnv ); 580 } 581 582 // ------------------------------------------------------------------- 583 // PROPFIND - propnames 584 // ------------------------------------------------------------------- 585 void SerfSession::PROPFIND( const rtl::OUString & inPath, 586 const Depth inDepth, 587 std::vector< DAVResourceInfo > & ioResInfo, 588 const DAVRequestEnvironment & rEnv ) 589 throw( DAVException ) 590 { 591 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 592 593 Init( rEnv ); 594 595 apr_status_t status = APR_SUCCESS; 596 SerfRequestProcessor aReqProc( *this, 597 inPath ); 598 aReqProc.processPropFind( inDepth, 599 ioResInfo, 600 status ); 601 602 if ( status == APR_SUCCESS && 603 aReqProc.mpDAVException == 0 && 604 ioResInfo.empty() ) 605 { 606 m_aEnv = DAVRequestEnvironment(); 607 throw DAVException( DAVException::DAV_HTTP_ERROR, inPath, (sal_uInt16)APR_EGENERAL ); 608 } 609 HandleError( aReqProc, 610 inPath, rEnv ); 611 } 612 613 // ------------------------------------------------------------------- 614 // PROPPATCH 615 // ------------------------------------------------------------------- 616 void SerfSession::PROPPATCH( const rtl::OUString & inPath, 617 const std::vector< ProppatchValue > & inValues, 618 const DAVRequestEnvironment & rEnv ) 619 throw( DAVException ) 620 { 621 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 622 623 Init( rEnv ); 624 625 apr_status_t status = APR_SUCCESS; 626 SerfRequestProcessor aReqProc( *this, 627 inPath ); 628 aReqProc.processPropPatch( inValues, 629 status ); 630 631 HandleError( aReqProc, 632 inPath, rEnv ); 633 } 634 635 // ------------------------------------------------------------------- 636 // HEAD 637 // ------------------------------------------------------------------- 638 void SerfSession::HEAD( const ::rtl::OUString & inPath, 639 const std::vector< ::rtl::OUString > & inHeaderNames, 640 DAVResource & ioResource, 641 const DAVRequestEnvironment & rEnv ) 642 throw( DAVException ) 643 { 644 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 645 646 Init( rEnv ); 647 648 m_bIsHeadRequestInProgress = true; 649 650 SerfRequestProcessor aReqProc( *this, 651 inPath ); 652 ioResource.uri = inPath; 653 ioResource.properties.clear(); 654 apr_status_t status = APR_SUCCESS; 655 aReqProc.processHead( inHeaderNames, 656 ioResource, 657 status ); 658 659 HandleError( aReqProc, 660 inPath, rEnv ); 661 m_bIsHeadRequestInProgress = false; 662 } 663 664 // ------------------------------------------------------------------- 665 // GET 666 // ------------------------------------------------------------------- 667 uno::Reference< io::XInputStream > 668 SerfSession::GET( const rtl::OUString & inPath, 669 const DAVRequestEnvironment & rEnv ) 670 throw ( DAVException ) 671 { 672 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 673 674 Init( rEnv ); 675 676 uno::Reference< SerfInputStream > xInputStream( new SerfInputStream ); 677 apr_status_t status = APR_SUCCESS; 678 SerfRequestProcessor aReqProc( *this, 679 inPath ); 680 aReqProc.processGet( xInputStream, 681 status ); 682 683 HandleError( aReqProc, 684 inPath, rEnv ); 685 686 return uno::Reference< io::XInputStream >( xInputStream.get() ); 687 } 688 689 // ------------------------------------------------------------------- 690 // GET 691 // ------------------------------------------------------------------- 692 void SerfSession::GET( const rtl::OUString & inPath, 693 uno::Reference< io::XOutputStream > & ioOutputStream, 694 const DAVRequestEnvironment & rEnv ) 695 throw ( DAVException ) 696 { 697 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 698 699 Init( rEnv ); 700 701 apr_status_t status = APR_SUCCESS; 702 SerfRequestProcessor aReqProc( *this, 703 inPath ); 704 aReqProc.processGet( ioOutputStream, 705 status ); 706 707 HandleError( aReqProc, 708 inPath, rEnv ); 709 } 710 711 // ------------------------------------------------------------------- 712 // GET 713 // ------------------------------------------------------------------- 714 uno::Reference< io::XInputStream > 715 SerfSession::GET( const rtl::OUString & inPath, 716 const std::vector< ::rtl::OUString > & inHeaderNames, 717 DAVResource & ioResource, 718 const DAVRequestEnvironment & rEnv ) 719 throw ( DAVException ) 720 { 721 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 722 723 Init( rEnv ); 724 725 SerfRequestProcessor aReqProc( *this, 726 inPath ); 727 uno::Reference< SerfInputStream > xInputStream( new SerfInputStream ); 728 ioResource.uri = inPath; 729 ioResource.properties.clear(); 730 apr_status_t status = APR_SUCCESS; 731 aReqProc.processGet( xInputStream, 732 inHeaderNames, 733 ioResource, 734 status ); 735 736 HandleError( aReqProc, 737 inPath, rEnv ); 738 739 return uno::Reference< io::XInputStream >( xInputStream.get() ); 740 } 741 742 743 // ------------------------------------------------------------------- 744 // GET 745 // ------------------------------------------------------------------- 746 void SerfSession::GET( const rtl::OUString & inPath, 747 uno::Reference< io::XOutputStream > & ioOutputStream, 748 const std::vector< ::rtl::OUString > & inHeaderNames, 749 DAVResource & ioResource, 750 const DAVRequestEnvironment & rEnv ) 751 throw ( DAVException ) 752 { 753 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 754 755 Init( rEnv ); 756 757 SerfRequestProcessor aReqProc( *this, 758 inPath ); 759 ioResource.uri = inPath; 760 ioResource.properties.clear(); 761 apr_status_t status = APR_SUCCESS; 762 aReqProc.processGet( ioOutputStream, 763 inHeaderNames, 764 ioResource, 765 status ); 766 767 HandleError( aReqProc, 768 inPath, rEnv ); 769 } 770 771 // ------------------------------------------------------------------- 772 // PUT 773 // ------------------------------------------------------------------- 774 void SerfSession::PUT( const rtl::OUString & inPath, 775 const uno::Reference< io::XInputStream > & inInputStream, 776 const DAVRequestEnvironment & rEnv ) 777 throw ( DAVException ) 778 { 779 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 780 781 Init( rEnv ); 782 783 SerfRequestProcessor aReqProc( *this, 784 inPath ); 785 uno::Sequence< sal_Int8 > aDataToSend; 786 if ( !getDataFromInputStream( inInputStream, aDataToSend, false ) ) 787 throw DAVException( DAVException::DAV_INVALID_ARG ); 788 apr_status_t status = APR_SUCCESS; 789 aReqProc.processPut( reinterpret_cast< const char * >( aDataToSend.getConstArray() ), 790 aDataToSend.getLength(), 791 status ); 792 793 HandleError( aReqProc, 794 inPath, rEnv ); 795 } 796 797 // ------------------------------------------------------------------- 798 // POST 799 // ------------------------------------------------------------------- 800 uno::Reference< io::XInputStream > 801 SerfSession::POST( const rtl::OUString & inPath, 802 const rtl::OUString & rContentType, 803 const rtl::OUString & rReferer, 804 const uno::Reference< io::XInputStream > & inInputStream, 805 const DAVRequestEnvironment & rEnv ) 806 throw ( DAVException ) 807 { 808 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 809 810 uno::Sequence< sal_Int8 > aDataToSend; 811 if ( !getDataFromInputStream( inInputStream, aDataToSend, true ) ) 812 { 813 throw DAVException( DAVException::DAV_INVALID_ARG ); 814 } 815 816 Init( rEnv ); 817 818 SerfRequestProcessor aReqProc( *this, 819 inPath ); 820 uno::Reference< SerfInputStream > xInputStream( new SerfInputStream ); 821 apr_status_t status = APR_SUCCESS; 822 aReqProc.processPost( reinterpret_cast< const char * >( aDataToSend.getConstArray() ), 823 aDataToSend.getLength(), 824 rContentType, 825 rReferer, 826 xInputStream, 827 status ); 828 829 HandleError( aReqProc, 830 inPath, rEnv ); 831 return uno::Reference< io::XInputStream >( xInputStream.get() ); 832 } 833 834 // ------------------------------------------------------------------- 835 // POST 836 // ------------------------------------------------------------------- 837 void SerfSession::POST( const rtl::OUString & inPath, 838 const rtl::OUString & rContentType, 839 const rtl::OUString & rReferer, 840 const uno::Reference< io::XInputStream > & inInputStream, 841 uno::Reference< io::XOutputStream > & oOutputStream, 842 const DAVRequestEnvironment & rEnv ) 843 throw ( DAVException ) 844 { 845 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 846 847 uno::Sequence< sal_Int8 > aDataToSend; 848 if ( !getDataFromInputStream( inInputStream, aDataToSend, true ) ) 849 { 850 throw DAVException( DAVException::DAV_INVALID_ARG ); 851 } 852 853 Init( rEnv ); 854 855 SerfRequestProcessor aReqProc( *this, 856 inPath ); 857 apr_status_t status = APR_SUCCESS; 858 aReqProc.processPost( reinterpret_cast< const char * >( aDataToSend.getConstArray() ), 859 aDataToSend.getLength(), 860 rContentType, 861 rReferer, 862 oOutputStream, 863 status ); 864 865 HandleError( aReqProc, 866 inPath, rEnv ); 867 } 868 869 // ------------------------------------------------------------------- 870 // MKCOL 871 // ------------------------------------------------------------------- 872 void SerfSession::MKCOL( const rtl::OUString & inPath, 873 const DAVRequestEnvironment & rEnv ) 874 throw ( DAVException ) 875 { 876 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 877 878 Init( rEnv ); 879 880 SerfRequestProcessor aReqProc( *this, 881 inPath ); 882 apr_status_t status = APR_SUCCESS; 883 aReqProc.processMkCol( status ); 884 885 HandleError( aReqProc, 886 inPath, rEnv ); 887 } 888 889 // ------------------------------------------------------------------- 890 // COPY 891 // ------------------------------------------------------------------- 892 void SerfSession::COPY( const rtl::OUString & inSourceURL, 893 const rtl::OUString & inDestinationURL, 894 const DAVRequestEnvironment & rEnv, 895 sal_Bool inOverWrite ) 896 throw ( DAVException ) 897 { 898 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 899 900 Init( rEnv ); 901 902 SerfUri theSourceUri( inSourceURL ); 903 SerfRequestProcessor aReqProc( *this, 904 theSourceUri.GetPath() ); 905 apr_status_t status = APR_SUCCESS; 906 aReqProc.processCopy( inDestinationURL, 907 (inOverWrite ? true : false), 908 status ); 909 910 HandleError( aReqProc, 911 inSourceURL, rEnv ); 912 } 913 914 // ------------------------------------------------------------------- 915 // MOVE 916 // ------------------------------------------------------------------- 917 void SerfSession::MOVE( const rtl::OUString & inSourceURL, 918 const rtl::OUString & inDestinationURL, 919 const DAVRequestEnvironment & rEnv, 920 sal_Bool inOverWrite ) 921 throw ( DAVException ) 922 { 923 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 924 925 Init( rEnv ); 926 927 SerfUri theSourceUri( inSourceURL ); 928 SerfRequestProcessor aReqProc( *this, 929 theSourceUri.GetPath() ); 930 apr_status_t status = APR_SUCCESS; 931 aReqProc.processMove( inDestinationURL, 932 (inOverWrite ? true : false), 933 status ); 934 935 HandleError( aReqProc, 936 inSourceURL, rEnv ); 937 } 938 939 // ------------------------------------------------------------------- 940 // DESTROY 941 // ------------------------------------------------------------------- 942 void SerfSession::DESTROY( const rtl::OUString & inPath, 943 const DAVRequestEnvironment & rEnv ) 944 throw ( DAVException ) 945 { 946 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 947 948 Init( rEnv ); 949 950 SerfRequestProcessor aReqProc( *this, 951 inPath ); 952 apr_status_t status = APR_SUCCESS; 953 aReqProc.processDelete( status ); 954 955 HandleError( aReqProc, 956 inPath, rEnv ); 957 } 958 959 // ------------------------------------------------------------------- 960 /* 961 namespace 962 { 963 sal_Int32 lastChanceToSendRefreshRequest( TimeValue const & rStart, 964 int timeout ) 965 { 966 TimeValue aEnd; 967 osl_getSystemTime( &aEnd ); 968 969 // Try to estimate a safe absolute time for sending the 970 // lock refresh request. 971 sal_Int32 lastChanceToSendRefreshRequest = -1; 972 if ( timeout != NE_TIMEOUT_INFINITE ) 973 { 974 sal_Int32 calltime = aEnd.Seconds - rStart.Seconds; 975 if ( calltime <= timeout ) 976 { 977 lastChanceToSendRefreshRequest 978 = aEnd.Seconds + timeout - calltime; 979 } 980 else 981 { 982 OSL_TRACE( "No chance to refresh lock before timeout!" ); 983 } 984 } 985 return lastChanceToSendRefreshRequest; 986 } 987 988 } // namespace 989 */ 990 // ------------------------------------------------------------------- 991 // LOCK (set new lock) 992 // ------------------------------------------------------------------- 993 void SerfSession::LOCK( const ::rtl::OUString & inPath, 994 ucb::Lock & /*rLock*/, 995 const DAVRequestEnvironment & rEnv ) 996 throw ( DAVException ) 997 { 998 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 999 1000 Init( rEnv ); 1001 1002 SerfRequestProcessor aReqProc( *this, 1003 inPath ); 1004 HandleError( aReqProc, 1005 inPath, rEnv ); 1006 /* Create a depth zero, exclusive write lock, with default timeout 1007 * (allowing a server to pick a default). token, owner and uri are 1008 * unset. */ 1009 /* 1010 SerfLock * theLock = ne_lock_create(); 1011 1012 // Set the lock uri 1013 ne_uri aUri; 1014 ne_uri_parse( rtl::OUStringToOString( makeAbsoluteURL( inPath ), 1015 RTL_TEXTENCODING_UTF8 ).getStr(), 1016 &aUri ); 1017 theLock->uri = aUri; 1018 1019 // Set the lock depth 1020 switch( rLock.Depth ) 1021 { 1022 case ucb::LockDepth_ZERO: 1023 theLock->depth = NE_DEPTH_ZERO; 1024 break; 1025 case ucb::LockDepth_ONE: 1026 theLock->depth = NE_DEPTH_ONE; 1027 break; 1028 case ucb::LockDepth_INFINITY: 1029 theLock->depth = NE_DEPTH_INFINITE; 1030 break; 1031 default: 1032 throw DAVException( DAVException::DAV_INVALID_ARG ); 1033 } 1034 1035 // Set the lock scope 1036 switch ( rLock.Scope ) 1037 { 1038 case ucb::LockScope_EXCLUSIVE: 1039 theLock->scope = ne_lockscope_exclusive; 1040 break; 1041 case ucb::LockScope_SHARED: 1042 theLock->scope = ne_lockscope_shared; 1043 break; 1044 default: 1045 throw DAVException( DAVException::DAV_INVALID_ARG ); 1046 } 1047 1048 // Set the lock timeout 1049 theLock->timeout = (long)rLock.Timeout; 1050 1051 // Set the lock owner 1052 rtl::OUString aValue; 1053 rLock.Owner >>= aValue; 1054 theLock->owner = 1055 ne_strdup( rtl::OUStringToOString( aValue, 1056 RTL_TEXTENCODING_UTF8 ).getStr() ); 1057 TimeValue startCall; 1058 osl_getSystemTime( &startCall ); 1059 1060 int theRetVal = ne_lock( m_pHttpSession, theLock ); 1061 1062 if ( theRetVal == NE_OK ) 1063 { 1064 m_aSerfLockStore.addLock( theLock, 1065 this, 1066 lastChanceToSendRefreshRequest( 1067 startCall, theLock->timeout ) ); 1068 1069 uno::Sequence< rtl::OUString > aTokens( 1 ); 1070 aTokens[ 0 ] = rtl::OUString::createFromAscii( theLock->token ); 1071 rLock.LockTokens = aTokens; 1072 1073 OSL_TRACE( "SerfSession::LOCK: created lock for %s. token: %s", 1074 rtl::OUStringToOString( makeAbsoluteURL( inPath ), 1075 RTL_TEXTENCODING_UTF8 ).getStr(), 1076 theLock->token ); 1077 } 1078 else 1079 { 1080 ne_lock_destroy( theLock ); 1081 1082 OSL_TRACE( "SerfSession::LOCK: obtaining lock for %s failed!", 1083 rtl::OUStringToOString( makeAbsoluteURL( inPath ), 1084 RTL_TEXTENCODING_UTF8 ).getStr() ); 1085 } 1086 1087 HandleError( theRetVal, inPath, rEnv ); 1088 */ 1089 } 1090 1091 // ------------------------------------------------------------------- 1092 // LOCK (refresh existing lock) 1093 // ------------------------------------------------------------------- 1094 sal_Int64 SerfSession::LOCK( const ::rtl::OUString & /*inPath*/, 1095 sal_Int64 nTimeout, 1096 const DAVRequestEnvironment & /*rEnv*/ ) 1097 throw ( DAVException ) 1098 { 1099 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 1100 1101 return nTimeout; 1102 /* 1103 // Try to get the neon lock from lock store 1104 SerfLock * theLock 1105 = m_aSerfLockStore.findByUri( makeAbsoluteURL( inPath ) ); 1106 if ( !theLock ) 1107 throw DAVException( DAVException::DAV_NOT_LOCKED ); 1108 1109 Init( rEnv ); 1110 1111 // refresh existing lock. 1112 theLock->timeout = static_cast< long >( nTimeout ); 1113 1114 TimeValue startCall; 1115 osl_getSystemTime( &startCall ); 1116 1117 int theRetVal = ne_lock_refresh( m_pHttpSession, theLock ); 1118 1119 if ( theRetVal == NE_OK ) 1120 { 1121 m_aSerfLockStore.updateLock( theLock, 1122 lastChanceToSendRefreshRequest( 1123 startCall, theLock->timeout ) ); 1124 } 1125 1126 HandleError( theRetVal, inPath, rEnv ); 1127 1128 return theLock->timeout; 1129 */ 1130 } 1131 1132 // ------------------------------------------------------------------- 1133 // LOCK (refresh existing lock) 1134 // ------------------------------------------------------------------- 1135 bool SerfSession::LOCK( SerfLock * /*pLock*/, 1136 sal_Int32 & /*rlastChanceToSendRefreshRequest*/ ) 1137 { 1138 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 1139 1140 return true; 1141 /* 1142 // refresh existing lock. 1143 1144 TimeValue startCall; 1145 osl_getSystemTime( &startCall ); 1146 1147 if ( ne_lock_refresh( m_pHttpSession, pLock ) == NE_OK ) 1148 { 1149 rlastChanceToSendRefreshRequest 1150 = lastChanceToSendRefreshRequest( startCall, pLock->timeout ); 1151 1152 OSL_TRACE( "Lock successfully refreshed." ); 1153 return true; 1154 } 1155 else 1156 { 1157 OSL_TRACE( "Lock not refreshed!" ); 1158 return false; 1159 } 1160 */ 1161 } 1162 1163 // ------------------------------------------------------------------- 1164 // UNLOCK 1165 // ------------------------------------------------------------------- 1166 void SerfSession::UNLOCK( const ::rtl::OUString & /*inPath*/, 1167 const DAVRequestEnvironment & /*rEnv*/ ) 1168 throw ( DAVException ) 1169 { 1170 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 1171 1172 /* 1173 // get the neon lock from lock store 1174 SerfLock * theLock 1175 = m_aSerfLockStore.findByUri( makeAbsoluteURL( inPath ) ); 1176 if ( !theLock ) 1177 throw DAVException( DAVException::DAV_NOT_LOCKED ); 1178 1179 Init( rEnv ); 1180 1181 int theRetVal = ne_unlock( m_pHttpSession, theLock ); 1182 1183 if ( theRetVal == NE_OK ) 1184 { 1185 m_aSerfLockStore.removeLock( theLock ); 1186 ne_lock_destroy( theLock ); 1187 } 1188 else 1189 { 1190 OSL_TRACE( "SerfSession::UNLOCK: unlocking of %s failed.", 1191 rtl::OUStringToOString( makeAbsoluteURL( inPath ), 1192 RTL_TEXTENCODING_UTF8 ).getStr() ); 1193 } 1194 1195 HandleError( theRetVal, inPath, rEnv ); 1196 */ 1197 } 1198 1199 // ------------------------------------------------------------------- 1200 // UNLOCK 1201 // ------------------------------------------------------------------- 1202 bool SerfSession::UNLOCK( SerfLock * /*pLock*/ ) 1203 { 1204 osl::Guard< osl::Mutex > theGuard( m_aMutex ); 1205 1206 return true; 1207 /* 1208 if ( ne_unlock( m_pHttpSession, pLock ) == NE_OK ) 1209 { 1210 OSL_TRACE( "UNLOCK succeeded." ); 1211 return true; 1212 } 1213 else 1214 { 1215 OSL_TRACE( "UNLOCK failed!" ); 1216 return false; 1217 } 1218 */ 1219 } 1220 1221 // ------------------------------------------------------------------- 1222 void SerfSession::abort() 1223 throw ( DAVException ) 1224 { 1225 // 11.11.09 (tkr): The following code lines causing crashes if 1226 // closing a ongoing connection. It turned out that this existing 1227 // solution doesn't work in multi-threading environments. 1228 // So I disabled them in 3.2. . Issue #73893# should fix it in OOo 3.3. 1229 //if ( m_pHttpSession ) 1230 // ne_close_connection( m_pHttpSession ); 1231 } 1232 1233 // ------------------------------------------------------------------- 1234 const ucbhelper::InternetProxyServer & SerfSession::getProxySettings() const 1235 { 1236 if ( m_aUri.GetScheme().equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "http" ) ) || 1237 m_aUri.GetScheme().equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "https" ) ) ) 1238 { 1239 return m_rProxyDecider.getProxy( m_aUri.GetScheme(), 1240 m_aUri.GetHost(), 1241 m_aUri.GetPort() ); 1242 } 1243 else 1244 { 1245 // TODO: figure out, if this case can occur 1246 return m_rProxyDecider.getProxy( m_aUri.GetScheme(), 1247 rtl::OUString() /* not used */, 1248 -1 /* not used */ ); 1249 } 1250 } 1251 1252 /* 1253 // ------------------------------------------------------------------- 1254 namespace { 1255 1256 bool containsLocktoken( const uno::Sequence< ucb::Lock > & rLocks, 1257 const char * token ) 1258 { 1259 for ( sal_Int32 n = 0; n < rLocks.getLength(); ++n ) 1260 { 1261 const uno::Sequence< rtl::OUString > & rTokens 1262 = rLocks[ n ].LockTokens; 1263 for ( sal_Int32 m = 0; m < rTokens.getLength(); ++m ) 1264 { 1265 if ( rTokens[ m ].equalsAscii( token ) ) 1266 return true; 1267 } 1268 } 1269 return false; 1270 } 1271 1272 } // namespace 1273 */ 1274 1275 // ------------------------------------------------------------------- 1276 bool SerfSession::removeExpiredLocktoken( const rtl::OUString & /*inURL*/, 1277 const DAVRequestEnvironment & /*rEnv*/ ) 1278 { 1279 return true; 1280 /* 1281 SerfLock * theLock = m_aSerfLockStore.findByUri( inURL ); 1282 if ( !theLock ) 1283 return false; 1284 1285 // do a lockdiscovery to check whether this lock is still valid. 1286 try 1287 { 1288 // @@@ Alternative: use ne_lock_discover() => less overhead 1289 1290 std::vector< DAVResource > aResources; 1291 std::vector< rtl::OUString > aPropNames; 1292 aPropNames.push_back( DAVProperties::LOCKDISCOVERY ); 1293 1294 PROPFIND( rEnv.m_aRequestURI, DAVZERO, aPropNames, aResources, rEnv ); 1295 1296 if ( aResources.size() == 0 ) 1297 return false; 1298 1299 std::vector< DAVPropertyValue >::const_iterator it 1300 = aResources[ 0 ].properties.begin(); 1301 std::vector< DAVPropertyValue >::const_iterator end 1302 = aResources[ 0 ].properties.end(); 1303 1304 while ( it != end ) 1305 { 1306 if ( (*it).Name.equals( DAVProperties::LOCKDISCOVERY ) ) 1307 { 1308 uno::Sequence< ucb::Lock > aLocks; 1309 if ( !( (*it).Value >>= aLocks ) ) 1310 return false; 1311 1312 if ( !containsLocktoken( aLocks, theLock->token ) ) 1313 { 1314 // expired! 1315 break; 1316 } 1317 1318 // still valid. 1319 return false; 1320 } 1321 ++it; 1322 } 1323 1324 // No lockdiscovery prop in propfind result / locktoken not found 1325 // in propfind result -> not locked 1326 OSL_TRACE( "SerfSession::removeExpiredLocktoken: Removing " 1327 " expired lock token for %s. token: %s", 1328 rtl::OUStringToOString( inURL, 1329 RTL_TEXTENCODING_UTF8 ).getStr(), 1330 theLock->token ); 1331 1332 m_aSerfLockStore.removeLock( theLock ); 1333 ne_lock_destroy( theLock ); 1334 return true; 1335 } 1336 catch ( DAVException const & ) 1337 { 1338 } 1339 return false; 1340 */ 1341 } 1342 1343 // ------------------------------------------------------------------- 1344 // HandleError 1345 // Common Error Handler 1346 // ------------------------------------------------------------------- 1347 void SerfSession::HandleError( SerfRequestProcessor& rReqProc, 1348 const rtl::OUString & /*inPath*/, 1349 const DAVRequestEnvironment & /*rEnv*/ ) 1350 throw ( DAVException ) 1351 { 1352 m_aEnv = DAVRequestEnvironment(); 1353 1354 if ( rReqProc.mpDAVException ) 1355 { 1356 DAVException* mpDAVExp( rReqProc.mpDAVException ); 1357 1358 serf_connection_reset( getSerfConnection() ); 1359 1360 throw DAVException( mpDAVExp->getError(), 1361 mpDAVExp->getData(), 1362 mpDAVExp->getStatus() ); 1363 } 1364 1365 /* 1366 // Map error code to DAVException. 1367 switch ( nError ) 1368 { 1369 case NE_OK: 1370 return; 1371 1372 case NE_ERROR: // Generic error 1373 { 1374 rtl::OUString aText = rtl::OUString::createFromAscii( 1375 ne_get_error( m_pHttpSession ) ); 1376 1377 sal_uInt16 code = makeStatusCode( aText ); 1378 1379 if ( code == SC_LOCKED ) 1380 { 1381 if ( m_aSerfLockStore.findByUri( 1382 makeAbsoluteURL( inPath ) ) == 0 ) 1383 { 1384 // locked by 3rd party 1385 throw DAVException( DAVException::DAV_LOCKED ); 1386 } 1387 else 1388 { 1389 // locked by ourself 1390 throw DAVException( DAVException::DAV_LOCKED_SELF ); 1391 } 1392 } 1393 1394 // Special handling for 400 and 412 status codes, which may indicate 1395 // that a lock previously obtained by us has been released meanwhile 1396 // by the server. Unfortunately, RFC is not clear at this point, 1397 // thus server implementations behave different... 1398 else if ( code == SC_BAD_REQUEST || code == SC_PRECONDITION_FAILED ) 1399 { 1400 if ( removeExpiredLocktoken( makeAbsoluteURL( inPath ), rEnv ) ) 1401 throw DAVException( DAVException::DAV_LOCK_EXPIRED ); 1402 } 1403 1404 throw DAVException( DAVException::DAV_HTTP_ERROR, aText, code ); 1405 } 1406 case NE_LOOKUP: // Name lookup failed. 1407 throw DAVException( DAVException::DAV_HTTP_LOOKUP, 1408 SerfUri::makeConnectionEndPointString( 1409 m_aHostName, m_nPort ) ); 1410 1411 case NE_AUTH: // User authentication failed on server 1412 throw DAVException( DAVException::DAV_HTTP_AUTH, 1413 SerfUri::makeConnectionEndPointString( 1414 m_aHostName, m_nPort ) ); 1415 1416 case NE_PROXYAUTH: // User authentication failed on proxy 1417 throw DAVException( DAVException::DAV_HTTP_AUTHPROXY, 1418 SerfUri::makeConnectionEndPointString( 1419 m_aProxyName, m_nProxyPort ) ); 1420 1421 case NE_CONNECT: // Could not connect to server 1422 throw DAVException( DAVException::DAV_HTTP_CONNECT, 1423 SerfUri::makeConnectionEndPointString( 1424 m_aHostName, m_nPort ) ); 1425 1426 case NE_TIMEOUT: // Connection timed out 1427 throw DAVException( DAVException::DAV_HTTP_TIMEOUT, 1428 SerfUri::makeConnectionEndPointString( 1429 m_aHostName, m_nPort ) ); 1430 1431 case NE_FAILED: // The precondition failed 1432 throw DAVException( DAVException::DAV_HTTP_FAILED, 1433 SerfUri::makeConnectionEndPointString( 1434 m_aHostName, m_nPort ) ); 1435 1436 case NE_RETRY: // Retry request (ne_end_request ONLY) 1437 throw DAVException( DAVException::DAV_HTTP_RETRY, 1438 SerfUri::makeConnectionEndPointString( 1439 m_aHostName, m_nPort ) ); 1440 1441 case NE_REDIRECT: 1442 { 1443 SerfUri aUri( ne_redirect_location( m_pHttpSession ) ); 1444 throw DAVException( 1445 DAVException::DAV_HTTP_REDIRECT, aUri.GetURI() ); 1446 } 1447 default: 1448 { 1449 OSL_TRACE( "SerfSession::HandleError : Unknown Serf error code!" ); 1450 throw DAVException( DAVException::DAV_HTTP_ERROR, 1451 rtl::OUString::createFromAscii( 1452 ne_get_error( m_pHttpSession ) ) ); 1453 } 1454 } 1455 */ 1456 } 1457 1458 // ------------------------------------------------------------------- 1459 // static 1460 bool 1461 SerfSession::getDataFromInputStream( 1462 const uno::Reference< io::XInputStream > & xStream, 1463 uno::Sequence< sal_Int8 > & rData, 1464 bool bAppendTrailingZeroByte ) 1465 { 1466 if ( xStream.is() ) 1467 { 1468 uno::Reference< io::XSeekable > xSeekable( xStream, uno::UNO_QUERY ); 1469 if ( xSeekable.is() ) 1470 { 1471 try 1472 { 1473 sal_Int32 nSize 1474 = sal::static_int_cast<sal_Int32>(xSeekable->getLength()); 1475 sal_Int32 nRead 1476 = xStream->readBytes( rData, nSize ); 1477 1478 if ( nRead == nSize ) 1479 { 1480 if ( bAppendTrailingZeroByte ) 1481 { 1482 rData.realloc( nSize + 1 ); 1483 rData[ nSize ] = sal_Int8( 0 ); 1484 } 1485 return true; 1486 } 1487 } 1488 catch ( io::NotConnectedException const & ) 1489 { 1490 // readBytes 1491 } 1492 catch ( io::BufferSizeExceededException const & ) 1493 { 1494 // readBytes 1495 } 1496 catch ( io::IOException const & ) 1497 { 1498 // getLength, readBytes 1499 } 1500 } 1501 else 1502 { 1503 try 1504 { 1505 uno::Sequence< sal_Int8 > aBuffer; 1506 sal_Int32 nPos = 0; 1507 1508 sal_Int32 nRead = xStream->readSomeBytes( aBuffer, 65536 ); 1509 while ( nRead > 0 ) 1510 { 1511 if ( rData.getLength() < ( nPos + nRead ) ) 1512 rData.realloc( nPos + nRead ); 1513 1514 aBuffer.realloc( nRead ); 1515 rtl_copyMemory( (void*)( rData.getArray() + nPos ), 1516 (const void*)aBuffer.getConstArray(), 1517 nRead ); 1518 nPos += nRead; 1519 1520 aBuffer.realloc( 0 ); 1521 nRead = xStream->readSomeBytes( aBuffer, 65536 ); 1522 } 1523 1524 if ( bAppendTrailingZeroByte ) 1525 { 1526 rData.realloc( nPos + 1 ); 1527 rData[ nPos ] = sal_Int8( 0 ); 1528 } 1529 return true; 1530 } 1531 catch ( io::NotConnectedException const & ) 1532 { 1533 // readBytes 1534 } 1535 catch ( io::BufferSizeExceededException const & ) 1536 { 1537 // readBytes 1538 } 1539 catch ( io::IOException const & ) 1540 { 1541 // readBytes 1542 } 1543 } 1544 } 1545 return false; 1546 } 1547 1548 // --------------------------------------------------------------------- 1549 sal_Bool 1550 SerfSession::isDomainMatch( rtl::OUString certHostName ) 1551 { 1552 rtl::OUString hostName = getHostName(); 1553 1554 if (hostName.equalsIgnoreAsciiCase( certHostName ) ) 1555 return sal_True; 1556 1557 if ( 0 == certHostName.indexOf( rtl::OUString::createFromAscii( "*" ) ) && 1558 hostName.getLength() >= certHostName.getLength() ) 1559 { 1560 rtl::OUString cmpStr = certHostName.copy( 1 ); 1561 1562 if ( hostName.matchIgnoreAsciiCase( 1563 cmpStr, hostName.getLength() - cmpStr.getLength() ) ) 1564 return sal_True; 1565 } 1566 return sal_False; 1567 } 1568 1569 /* 1570 // --------------------------------------------------------------------- 1571 rtl::OUString SerfSession::makeAbsoluteURL( rtl::OUString const & rURL ) const 1572 { 1573 try 1574 { 1575 // Is URL relative or already absolute? 1576 if ( rURL[ 0 ] != sal_Unicode( '/' ) ) 1577 { 1578 // absolute. 1579 return rtl::OUString( rURL ); 1580 } 1581 else 1582 { 1583 ne_uri aUri; 1584 memset( &aUri, 0, sizeof( aUri ) ); 1585 1586 ne_fill_server_uri( m_pHttpSession, &aUri ); 1587 aUri.path 1588 = ne_strdup( rtl::OUStringToOString( 1589 rURL, RTL_TEXTENCODING_UTF8 ).getStr() ); 1590 SerfUri aSerfUri( &aUri ); 1591 ne_uri_free( &aUri ); 1592 return aSerfUri.GetURI(); 1593 } 1594 } 1595 catch ( DAVException const & ) 1596 { 1597 } 1598 // error. 1599 return rtl::OUString(); 1600 } 1601 */ 1602