LCOV - code coverage report
Current view: top level - svl/source/misc - urihelper.cxx (source / functions) Hit Total Coverage
Test: commit e02a6cb2c3e2b23b203b422e4e0680877f232636 Lines: 0 299 0.0 %
Date: 2014-04-14 Functions: 0 15 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : #include <svl/urihelper.hxx>
      21             : #include "com/sun/star/ucb/Command.hpp"
      22             : #include "com/sun/star/ucb/IllegalIdentifierException.hpp"
      23             : #include "com/sun/star/ucb/UniversalContentBroker.hpp"
      24             : #include "com/sun/star/ucb/UnsupportedCommandException.hpp"
      25             : #include "com/sun/star/ucb/XCommandEnvironment.hpp"
      26             : #include "com/sun/star/ucb/XCommandProcessor.hpp"
      27             : #include "com/sun/star/ucb/XContent.hpp"
      28             : #include "com/sun/star/ucb/XUniversalContentBroker.hpp"
      29             : #include "com/sun/star/uno/Any.hxx"
      30             : #include "com/sun/star/uno/Exception.hpp"
      31             : #include "com/sun/star/uno/Reference.hxx"
      32             : #include "com/sun/star/uno/RuntimeException.hpp"
      33             : #include "com/sun/star/uno/XComponentContext.hpp"
      34             : #include "com/sun/star/uri/UriReferenceFactory.hpp"
      35             : #include "com/sun/star/uri/XUriReference.hpp"
      36             : #include "com/sun/star/uri/XUriReferenceFactory.hpp"
      37             : #include "comphelper/processfactory.hxx"
      38             : #include "osl/diagnose.h"
      39             : #include "rtl/ustrbuf.hxx"
      40             : #include "rtl/ustring.h"
      41             : #include "rtl/ustring.hxx"
      42             : #include "sal/types.h"
      43             : #include <tools/inetmime.hxx>
      44             : #include <unotools/charclass.hxx>
      45             : #include "rtl/instance.hxx"
      46             : 
      47             : using namespace com::sun::star;
      48             : 
      49             : 
      50             : //  SmartRel2Abs
      51             : 
      52             : 
      53           0 : OUString URIHelper::SmartRel2Abs(INetURLObject const & rTheBaseURIRef,
      54             :                                  OUString const & rTheRelURIRef,
      55             :                                  Link const & rMaybeFileHdl,
      56             :                                  bool bCheckFileExists,
      57             :                                  bool bIgnoreFragment,
      58             :                                  INetURLObject::EncodeMechanism eEncodeMechanism,
      59             :                                  INetURLObject::DecodeMechanism eDecodeMechanism,
      60             :                                  rtl_TextEncoding eCharset,
      61             :                                  bool bRelativeNonURIs,
      62             :                                  INetURLObject::FSysStyle eStyle)
      63             : {
      64             :     // Backwards compatibility:
      65           0 :     if( rTheRelURIRef.startsWith("#") )
      66           0 :         return rTheRelURIRef;
      67             : 
      68           0 :     INetURLObject aAbsURIRef;
      69           0 :     if (rTheBaseURIRef.HasError())
      70           0 :         aAbsURIRef. SetSmartURL(rTheRelURIRef, eEncodeMechanism, eCharset, eStyle);
      71             :     else
      72             :     {
      73             :         bool bWasAbsolute;
      74           0 :         aAbsURIRef = rTheBaseURIRef.smartRel2Abs(rTheRelURIRef,
      75             :                                                  bWasAbsolute,
      76             :                                                  bIgnoreFragment,
      77             :                                                  eEncodeMechanism,
      78             :                                                  eCharset,
      79             :                                                  bRelativeNonURIs,
      80           0 :                                                  eStyle);
      81           0 :         if (bCheckFileExists
      82           0 :             && !bWasAbsolute
      83           0 :             && (aAbsURIRef.GetProtocol() == INET_PROT_FILE))
      84             :         {
      85           0 :             INetURLObject aNonFileURIRef;
      86             :             aNonFileURIRef.SetSmartURL(rTheRelURIRef,
      87             :                                        eEncodeMechanism,
      88             :                                        eCharset,
      89           0 :                                        eStyle);
      90           0 :             if (!aNonFileURIRef.HasError()
      91           0 :                 && aNonFileURIRef.GetProtocol() != INET_PROT_FILE)
      92             :             {
      93           0 :                 bool bMaybeFile = false;
      94           0 :                 if (rMaybeFileHdl.IsSet())
      95             :                 {
      96           0 :                     OUString aFilePath(rTheRelURIRef);
      97           0 :                     bMaybeFile = rMaybeFileHdl.Call(&aFilePath) != 0;
      98             :                 }
      99           0 :                 if (!bMaybeFile)
     100           0 :                     aAbsURIRef = aNonFileURIRef;
     101           0 :             }
     102             :         }
     103             :     }
     104           0 :     return aAbsURIRef.GetMainURL(eDecodeMechanism, eCharset);
     105             : }
     106             : 
     107             : 
     108             : //  SetMaybeFileHdl
     109             : 
     110             : 
     111             : namespace { struct MaybeFileHdl : public rtl::Static< Link, MaybeFileHdl > {}; }
     112             : 
     113           0 : void URIHelper::SetMaybeFileHdl(Link const & rTheMaybeFileHdl)
     114             : {
     115           0 :     MaybeFileHdl::get() = rTheMaybeFileHdl;
     116           0 : }
     117             : 
     118             : 
     119             : //  GetMaybeFileHdl
     120             : 
     121             : 
     122           0 : Link URIHelper::GetMaybeFileHdl()
     123             : {
     124           0 :     return MaybeFileHdl::get();
     125             : }
     126             : 
     127             : namespace {
     128             : 
     129           0 : bool isAbsoluteHierarchicalUriReference(
     130             :     css::uno::Reference< css::uri::XUriReference > const & uriReference)
     131             : {
     132           0 :     return uriReference.is() && uriReference->isAbsolute()
     133           0 :         && uriReference->isHierarchical() && !uriReference->hasRelativePath();
     134             : }
     135             : 
     136             : // To improve performance, assume that if for any prefix URL of a given
     137             : // hierarchical URL either a UCB content cannot be created, or the UCB content
     138             : // does not support the getCasePreservingURL command, then this will hold for
     139             : // any other prefix URL of the given URL, too:
     140             : enum Result { Success, GeneralFailure, SpecificFailure };
     141             : 
     142           0 : Result normalizePrefix( css::uno::Reference< css::ucb::XUniversalContentBroker > const & broker,
     143             :                         OUString const & uri, OUString * normalized)
     144             : {
     145             :     OSL_ASSERT(broker.is() && normalized != 0);
     146           0 :     css::uno::Reference< css::ucb::XContent > content;
     147             :     try {
     148           0 :         content = broker->queryContent(broker->createContentIdentifier(uri));
     149           0 :     } catch (css::ucb::IllegalIdentifierException &) {}
     150           0 :     if (!content.is()) {
     151           0 :         return GeneralFailure;
     152             :     }
     153             :     try {
     154             :         #if OSL_DEBUG_LEVEL > 0
     155             :         bool ok =
     156             :         #endif
     157             :             (css::uno::Reference< css::ucb::XCommandProcessor >(
     158           0 :                    content, css::uno::UNO_QUERY_THROW)->execute(
     159             :                        css::ucb::Command("getCasePreservingURL",
     160             :                            -1, css::uno::Any()),
     161             :                        0,
     162           0 :                        css::uno::Reference< css::ucb::XCommandEnvironment >())
     163           0 :                >>= *normalized);
     164             :         OSL_ASSERT(ok);
     165           0 :     } catch (css::uno::RuntimeException &) {
     166           0 :         throw;
     167           0 :     } catch (css::ucb::UnsupportedCommandException &) {
     168           0 :         return GeneralFailure;
     169           0 :     } catch (css::uno::Exception &) {
     170           0 :         return SpecificFailure;
     171             :     }
     172           0 :     return Success;
     173             : }
     174             : 
     175           0 : OUString normalize(
     176             :     css::uno::Reference< css::ucb::XUniversalContentBroker > const & broker,
     177             :     css::uno::Reference< css::uri::XUriReferenceFactory > const & uriFactory,
     178             :     OUString const & uriReference)
     179             : {
     180             :     // normalizePrefix can potentially fail (a typically example being a file
     181             :     // URL that denotes a non-existing resource); in such a case, try to
     182             :     // normalize as long a prefix of the given URL as possible (i.e., normalize
     183             :     // all the existing directories within the path):
     184           0 :     OUString normalized;
     185           0 :     sal_Int32 n = uriReference.indexOf('#');
     186           0 :     normalized = n == -1 ? uriReference : uriReference.copy(0, n);
     187           0 :     switch (normalizePrefix(broker, normalized, &normalized)) {
     188             :     case Success:
     189           0 :         return n == -1 ? normalized : normalized + uriReference.copy(n);
     190             :     case GeneralFailure:
     191           0 :         return uriReference;
     192             :     case SpecificFailure:
     193             :     default:
     194           0 :         break;
     195             :     }
     196             :     css::uno::Reference< css::uri::XUriReference > ref(
     197           0 :         uriFactory->parse(uriReference));
     198           0 :     if (!isAbsoluteHierarchicalUriReference(ref)) {
     199           0 :         return uriReference;
     200             :     }
     201           0 :     sal_Int32 count = ref->getPathSegmentCount();
     202           0 :     if (count < 2) {
     203           0 :         return uriReference;
     204             :     }
     205           0 :     OUStringBuffer head(ref->getScheme());
     206           0 :     head.append(':');
     207           0 :     if (ref->hasAuthority()) {
     208           0 :         head.append("//");
     209           0 :         head.append(ref->getAuthority());
     210             :     }
     211           0 :     for (sal_Int32 i = count - 1; i > 0; --i) {
     212           0 :         OUStringBuffer buf(head);
     213           0 :         for (sal_Int32 j = 0; j < i; ++j) {
     214           0 :             buf.append('/');
     215           0 :             buf.append(ref->getPathSegment(j));
     216             :         }
     217           0 :         normalized = buf.makeStringAndClear();
     218           0 :         if (normalizePrefix(broker, normalized, &normalized) != SpecificFailure)
     219             :         {
     220           0 :             buf.append(normalized);
     221             :             css::uno::Reference< css::uri::XUriReference > preRef(
     222           0 :                 uriFactory->parse(normalized));
     223           0 :             if (!isAbsoluteHierarchicalUriReference(preRef)) {
     224             :                 // This could only happen if something is inconsistent:
     225           0 :                 break;
     226             :             }
     227           0 :             sal_Int32 preCount = preRef->getPathSegmentCount();
     228             :             // normalizePrefix may have added or removed a final slash:
     229           0 :             if (preCount != i) {
     230           0 :                 if (preCount == i - 1) {
     231           0 :                     buf.append('/');
     232           0 :                 } else if (preCount - 1 == i && !buf.isEmpty()
     233           0 :                            && buf[buf.getLength() - 1] == '/')
     234             :                 {
     235           0 :                     buf.setLength(buf.getLength() - 1);
     236             :                 } else {
     237             :                     // This could only happen if something is inconsistent:
     238           0 :                     break;
     239             :                 }
     240             :             }
     241           0 :             for (sal_Int32 j = i; j < count; ++j) {
     242           0 :                 buf.append('/');
     243           0 :                 buf.append(ref->getPathSegment(j));
     244             :             }
     245           0 :             if (ref->hasQuery()) {
     246           0 :                 buf.append('?');
     247           0 :                 buf.append(ref->getQuery());
     248             :             }
     249           0 :             if (ref->hasFragment()) {
     250           0 :                 buf.append('#');
     251           0 :                 buf.append(ref->getFragment());
     252             :             }
     253           0 :             return buf.makeStringAndClear();
     254             :         }
     255           0 :     }
     256           0 :     return uriReference;
     257             : }
     258             : 
     259             : }
     260             : 
     261             : css::uno::Reference< css::uri::XUriReference >
     262           0 : URIHelper::normalizedMakeRelative(
     263             :     css::uno::Reference< css::uno::XComponentContext > const & context,
     264             :     OUString const & baseUriReference, OUString const & uriReference)
     265             : {
     266             :     OSL_ASSERT(context.is());
     267             :     css::uno::Reference< css::ucb::XUniversalContentBroker > broker(
     268           0 :         css::ucb::UniversalContentBroker::create(context));
     269             :     css::uno::Reference< css::uri::XUriReferenceFactory > uriFactory(
     270           0 :         css::uri::UriReferenceFactory::create(context));
     271           0 :     return uriFactory->makeRelative(
     272           0 :         uriFactory->parse(normalize(broker, uriFactory, baseUriReference)),
     273           0 :         uriFactory->parse(normalize(broker, uriFactory, uriReference)), true,
     274           0 :         true, false);
     275             : }
     276             : 
     277           0 : OUString URIHelper::simpleNormalizedMakeRelative(
     278             :     OUString const & baseUriReference, OUString const & uriReference)
     279             : {
     280             :     com::sun::star::uno::Reference< com::sun::star::uri::XUriReference > rel(
     281             :         URIHelper::normalizedMakeRelative(
     282             :             comphelper::getProcessComponentContext(), baseUriReference,
     283           0 :             uriReference));
     284           0 :     return rel.is() ? rel->getUriReference() : uriReference;
     285             : }
     286             : 
     287             : 
     288             : //  FindFirstURLInText
     289             : 
     290             : 
     291             : namespace {
     292             : 
     293           0 : inline sal_Int32 nextChar(OUString const & rStr, sal_Int32 nPos)
     294             : {
     295           0 :     return INetMIME::isHighSurrogate(rStr[nPos])
     296           0 :            && rStr.getLength() - nPos >= 2
     297           0 :            && INetMIME::isLowSurrogate(rStr[nPos + 1]) ?
     298           0 :         nPos + 2 : nPos + 1;
     299             : }
     300             : 
     301           0 : bool isBoundary1(CharClass const & rCharClass, OUString const & rStr,
     302             :                  sal_Int32 nPos, sal_Int32 nEnd)
     303             : {
     304           0 :     if (nPos == nEnd)
     305           0 :         return true;
     306           0 :     if (rCharClass.isLetterNumeric(rStr, nPos))
     307           0 :         return false;
     308           0 :     switch (rStr[nPos])
     309             :     {
     310             :     case '$':
     311             :     case '%':
     312             :     case '&':
     313             :     case '-':
     314             :     case '/':
     315             :     case '@':
     316             :     case '\\':
     317           0 :         return false;
     318             :     default:
     319           0 :         return true;
     320             :     }
     321             : }
     322             : 
     323           0 : bool isBoundary2(CharClass const & rCharClass, OUString const & rStr,
     324             :                  sal_Int32 nPos, sal_Int32 nEnd)
     325             : {
     326           0 :     if (nPos == nEnd)
     327           0 :         return true;
     328           0 :     if (rCharClass.isLetterNumeric(rStr, nPos))
     329           0 :         return false;
     330           0 :     switch (rStr[nPos])
     331             :     {
     332             :     case '!':
     333             :     case '#':
     334             :     case '$':
     335             :     case '%':
     336             :     case '&':
     337             :     case '\'':
     338             :     case '*':
     339             :     case '+':
     340             :     case '-':
     341             :     case '/':
     342             :     case '=':
     343             :     case '?':
     344             :     case '@':
     345             :     case '^':
     346             :     case '_':
     347             :     case '`':
     348             :     case '{':
     349             :     case '|':
     350             :     case '}':
     351             :     case '~':
     352           0 :         return false;
     353             :     default:
     354           0 :         return true;
     355             :     }
     356             : }
     357             : 
     358           0 : bool checkWChar(CharClass const & rCharClass, OUString const & rStr,
     359             :                 sal_Int32 * pPos, sal_Int32 * pEnd, bool bBackslash = false,
     360             :                 bool bPipe = false)
     361             : {
     362           0 :     sal_Unicode c = rStr[*pPos];
     363           0 :     if (rtl::isAscii(c))
     364             :     {
     365             :         static sal_uInt8 const aMap[128]
     366             :             = { 0, 0, 0, 0, 0, 0, 0, 0,
     367             :                 0, 0, 0, 0, 0, 0, 0, 0,
     368             :                 0, 0, 0, 0, 0, 0, 0, 0,
     369             :                 0, 0, 0, 0, 0, 0, 0, 0,
     370             :                 0, 1, 0, 0, 4, 4, 4, 1,   //  !"#$%&'
     371             :                 1, 1, 1, 1, 1, 4, 1, 4,   // ()*+,-./
     372             :                 4, 4, 4, 4, 4, 4, 4, 4,   // 01234567
     373             :                 4, 4, 1, 1, 0, 1, 0, 1,   // 89:;<=>?
     374             :                 4, 4, 4, 4, 4, 4, 4, 4,   // @ABCDEFG
     375             :                 4, 4, 4, 4, 4, 4, 4, 4,   // HIJKLMNO
     376             :                 4, 4, 4, 4, 4, 4, 4, 4,   // PQRSTUVW
     377             :                 4, 4, 4, 1, 2, 1, 0, 1,   // XYZ[\]^_
     378             :                 0, 4, 4, 4, 4, 4, 4, 4,   // `abcdefg
     379             :                 4, 4, 4, 4, 4, 4, 4, 4,   // hijklmno
     380             :                 4, 4, 4, 4, 4, 4, 4, 4,   // pqrstuvw
     381             :                 4, 4, 4, 0, 3, 0, 1, 0 }; // xyz{|}~
     382           0 :         switch (aMap[c])
     383             :         {
     384             :             default: // not uric
     385           0 :                 return false;
     386             : 
     387             :             case 1: // uric
     388           0 :                 ++(*pPos);
     389           0 :                 return true;
     390             : 
     391             :             case 2: // "\"
     392           0 :                 if (bBackslash)
     393             :                 {
     394           0 :                     *pEnd = ++(*pPos);
     395           0 :                     return true;
     396             :                 }
     397             :                 else
     398           0 :                     return false;
     399             : 
     400             :             case 3: // "|"
     401           0 :                 if (bPipe)
     402             :                 {
     403           0 :                     *pEnd = ++(*pPos);
     404           0 :                     return true;
     405             :                 }
     406             :                 else
     407           0 :                     return false;
     408             : 
     409             :             case 4: // alpha, digit, "$", "%", "&", "-", "/", "@" (see
     410             :                     // isBoundary1)
     411           0 :                 *pEnd = ++(*pPos);
     412           0 :                 return true;
     413             :         }
     414             :     }
     415           0 :     else if (rCharClass.isLetterNumeric(rStr, *pPos))
     416             :     {
     417           0 :         *pEnd = *pPos = nextChar(rStr, *pPos);
     418           0 :         return true;
     419             :     }
     420             :     else
     421           0 :         return false;
     422             : }
     423             : 
     424           0 : sal_uInt32 scanDomain(OUString const & rStr, sal_Int32 * pPos,
     425             :                       sal_Int32 nEnd)
     426             : {
     427           0 :     sal_Unicode const * pBuffer = rStr.getStr();
     428           0 :     sal_Unicode const * p = pBuffer + *pPos;
     429           0 :     sal_uInt32 nLabels = INetURLObject::scanDomain(p, pBuffer + nEnd, false);
     430           0 :     *pPos = sal::static_int_cast< sal_Int32 >(p - pBuffer);
     431           0 :     return nLabels;
     432             : }
     433             : 
     434             : }
     435             : 
     436           0 : OUString URIHelper::FindFirstURLInText(OUString const & rText,
     437             :                                        sal_Int32 & rBegin,
     438             :                                        sal_Int32 & rEnd,
     439             :                                        CharClass const & rCharClass,
     440             :                                        INetURLObject::EncodeMechanism eMechanism,
     441             :                                        rtl_TextEncoding eCharset,
     442             :                                        INetURLObject::FSysStyle eStyle)
     443             : {
     444           0 :     if (!(rBegin <= rEnd && rEnd <= rText.getLength()))
     445           0 :         return OUString();
     446             : 
     447             :     // Search for the first substring of [rBegin..rEnd[ that matches any of the
     448             :     // following productions (for which the appropriate style bit is set in
     449             :     // eStyle, if applicable).
     450             : 
     451             :     // 1st Production (known scheme):
     452             :     //    \B1 <one of the known schemes, except file> ":" 1*wchar ["#" 1*wchar]
     453             :     //        \B1
     454             : 
     455             :     // 2nd Production (file):
     456             :     //    \B1 "FILE:" 1*(wchar / "\" / "|") ["#" 1*wchar] \B1
     457             : 
     458             :     // 3rd Production (ftp):
     459             :     //    \B1 "FTP" 2*("." label) ["/" *wchar] ["#" 1*wchar] \B1
     460             : 
     461             :     // 4th Production (http):
     462             :     //    \B1 "WWW" 2*("." label) ["/" *wchar] ["#" 1*wchar] \B1
     463             : 
     464             :     // 5th Production (mailto):
     465             :     //    \B2 local-part "@" domain \B1
     466             : 
     467             :     // 6th Production (UNC file):
     468             :     //    \B1 "\\" domain "\" *(wchar / "\") \B1
     469             : 
     470             :     // 7th Production (DOS file):
     471             :     //    \B1 ALPHA ":\" *(wchar / "\") \B1
     472             : 
     473             :     // 8th Production (Unix-like DOS file):
     474             :     //    \B1 ALPHA ":/" *(wchar / "\") \B1
     475             : 
     476             :     // The productions use the following auxiliary rules.
     477             : 
     478             :     //    local-part = atom *("." atom)
     479             :     //    atom = 1*(alphanum / "!" / "#" / "$" / "%" / "&" / "'" / "*" / "+"
     480             :     //              / "-" / "/" / "=" / "?" / "^" / "_" / "`" / "{" / "|" / "}"
     481             :     //              / "~")
     482             :     //    domain = label *("." label)
     483             :     //    label = alphanum [*(alphanum / "-") alphanum]
     484             :     //    alphanum = ALPHA / DIGIT
     485             :     //    wchar = <any uric character (ignoring the escaped rule), or "%", or
     486             :     //             a letter or digit (according to rCharClass)>
     487             : 
     488             :     // "\B1" (boundary 1) stands for the beginning or end of the block of text,
     489             :     // or a character that is neither (a) a letter or digit (according to
     490             :     // rCharClass), nor (b) any of "$", "%", "&", "-", "/", "@", or "\".
     491             :     // (FIXME:  What was the rationale for this set of punctuation characters?)
     492             : 
     493             :     // "\B2" (boundary 2) stands for the beginning or end of the block of text,
     494             :     // or a character that is neither (a) a letter or digit (according to
     495             :     // rCharClass), nor (b) any of "!", "#", "$", "%", "&", "'", "*", "+", "-",
     496             :     // "/", "=", "?", "@", "^", "_", "`", "{", "|", "}", or "~" (i.e., an RFC
     497             :     // 822 <atom> character, or "@" from \B1's set above).
     498             : 
     499             :     // Productions 1--4, and 6--8 try to find a maximum-length match, but they
     500             :     // stop at the first <wchar> character that is a "\B1" character which is
     501             :     // only followed by "\B1" characters (taking "\" and "|" characters into
     502             :     // account appropriately).  Production 5 simply tries to find a maximum-
     503             :     // length match.
     504             : 
     505             :     // Productions 1--4 use the given eMechanism and eCharset.  Productions 5--9
     506             :     // use ENCODE_ALL.
     507             : 
     508             :     // Productions 6--9 are only applicable if the FSYS_DOS bit is set in
     509             :     // eStyle.
     510             : 
     511           0 :     bool bBoundary1 = true;
     512           0 :     bool bBoundary2 = true;
     513           0 :     for (sal_Int32 nPos = rBegin; nPos != rEnd; nPos = nextChar(rText, nPos))
     514             :     {
     515           0 :         sal_Unicode c = rText[nPos];
     516           0 :         if (bBoundary1)
     517             :         {
     518           0 :             if (rtl::isAsciiAlpha(c))
     519             :             {
     520           0 :                 sal_Int32 i = nPos;
     521           0 :                 INetProtocol eScheme = INetURLObject::CompareProtocolScheme(rText.copy(i, rEnd - i));
     522           0 :                 if (eScheme == INET_PROT_FILE) // 2nd
     523             :                 {
     524           0 :                     while (rText[i++] != ':') ;
     525           0 :                     sal_Int32 nPrefixEnd = i;
     526           0 :                     sal_Int32 nUriEnd = i;
     527           0 :                     while (i != rEnd
     528           0 :                            && checkWChar(rCharClass, rText, &i, &nUriEnd, true,
     529           0 :                                          true)) ;
     530           0 :                     if (i != nPrefixEnd && i != rEnd && rText[i] == '#')
     531             :                     {
     532           0 :                         ++i;
     533           0 :                         while (i != rEnd
     534           0 :                                && checkWChar(rCharClass, rText, &i, &nUriEnd)) ;
     535             :                     }
     536           0 :                     if (nUriEnd != nPrefixEnd
     537           0 :                         && isBoundary1(rCharClass, rText, nUriEnd, rEnd))
     538             :                     {
     539             :                         INetURLObject aUri(rText.copy(nPos, nUriEnd - nPos),
     540             :                                            INET_PROT_FILE, eMechanism, eCharset,
     541           0 :                                            eStyle);
     542           0 :                         if (!aUri.HasError())
     543             :                         {
     544           0 :                             rBegin = nPos;
     545           0 :                             rEnd = nUriEnd;
     546             :                             return
     547           0 :                                 aUri.GetMainURL(INetURLObject::DECODE_TO_IURI);
     548           0 :                         }
     549             :                     }
     550             :                 }
     551           0 :                 else if (eScheme != INET_PROT_NOT_VALID) // 1st
     552             :                 {
     553           0 :                     while (rText[i++] != ':') ;
     554           0 :                     sal_Int32 nPrefixEnd = i;
     555           0 :                     sal_Int32 nUriEnd = i;
     556           0 :                     while (i != rEnd
     557           0 :                            && checkWChar(rCharClass, rText, &i, &nUriEnd)) ;
     558           0 :                     if (i != nPrefixEnd && i != rEnd && rText[i] == '#')
     559             :                     {
     560           0 :                         ++i;
     561           0 :                         while (i != rEnd
     562           0 :                                && checkWChar(rCharClass, rText, &i, &nUriEnd)) ;
     563             :                     }
     564           0 :                     if (nUriEnd != nPrefixEnd
     565           0 :                         && (isBoundary1(rCharClass, rText, nUriEnd, rEnd)
     566           0 :                             || rText[nUriEnd] == '\\'))
     567             :                     {
     568             :                         INetURLObject aUri(rText.copy(nPos, nUriEnd - nPos),
     569             :                                            INET_PROT_HTTP, eMechanism,
     570           0 :                                            eCharset);
     571           0 :                         if (!aUri.HasError())
     572             :                         {
     573           0 :                             rBegin = nPos;
     574           0 :                             rEnd = nUriEnd;
     575             :                             return
     576           0 :                                 aUri.GetMainURL(INetURLObject::DECODE_TO_IURI);
     577           0 :                         }
     578             :                     }
     579             :                 }
     580             : 
     581             :                 // 3rd, 4th:
     582           0 :                 i = nPos;
     583           0 :                 sal_uInt32 nLabels = scanDomain(rText, &i, rEnd);
     584           0 :                 if (nLabels >= 3
     585           0 :                     && rText[nPos + 3] == '.'
     586           0 :                     && (((rText[nPos] == 'w'
     587           0 :                           || rText[nPos] == 'W')
     588           0 :                          && (rText[nPos + 1] == 'w'
     589           0 :                              || rText[nPos + 1] == 'W')
     590           0 :                          && (rText[nPos + 2] == 'w'
     591           0 :                              || rText[nPos + 2] == 'W'))
     592           0 :                         || ((rText[nPos] == 'f'
     593           0 :                              || rText[nPos] == 'F')
     594           0 :                             && (rText[nPos + 1] == 't'
     595           0 :                                 || rText[nPos + 1] == 'T')
     596           0 :                             && (rText[nPos + 2] == 'p'
     597           0 :                                 || rText[nPos + 2] == 'P'))))
     598             :                     // (note that rText.GetChar(nPos + 3) is guaranteed to be
     599             :                     // valid)
     600             :                 {
     601           0 :                     sal_Int32 nUriEnd = i;
     602           0 :                     if (i != rEnd && rText[i] == '/')
     603             :                     {
     604           0 :                         nUriEnd = ++i;
     605           0 :                         while (i != rEnd
     606           0 :                                && checkWChar(rCharClass, rText, &i, &nUriEnd)) ;
     607             :                     }
     608           0 :                     if (i != rEnd && rText[i] == '#')
     609             :                     {
     610           0 :                         ++i;
     611           0 :                         while (i != rEnd
     612           0 :                                && checkWChar(rCharClass, rText, &i, &nUriEnd)) ;
     613             :                     }
     614           0 :                     if (isBoundary1(rCharClass, rText, nUriEnd, rEnd)
     615           0 :                         || rText[nUriEnd] == '\\')
     616             :                     {
     617             :                         INetURLObject aUri(rText.copy(nPos, nUriEnd - nPos),
     618             :                                            INET_PROT_HTTP, eMechanism,
     619           0 :                                            eCharset);
     620           0 :                         if (!aUri.HasError())
     621             :                         {
     622           0 :                             rBegin = nPos;
     623           0 :                             rEnd = nUriEnd;
     624             :                             return
     625           0 :                                 aUri.GetMainURL(INetURLObject::DECODE_TO_IURI);
     626           0 :                         }
     627             :                     }
     628             :                 }
     629             : 
     630           0 :                 if ((eStyle & INetURLObject::FSYS_DOS) != 0 && rEnd - nPos >= 3
     631           0 :                     && rText[nPos + 1] == ':'
     632           0 :                     && (rText[nPos + 2] == '/'
     633           0 :                         || rText[nPos + 2] == '\\')) // 7th, 8th
     634             :                 {
     635           0 :                     i = nPos + 3;
     636           0 :                     sal_Int32 nUriEnd = i;
     637           0 :                     while (i != rEnd
     638           0 :                            && checkWChar(rCharClass, rText, &i, &nUriEnd)) ;
     639           0 :                     if (isBoundary1(rCharClass, rText, nUriEnd, rEnd))
     640             :                     {
     641             :                         INetURLObject aUri(rText.copy(nPos, nUriEnd - nPos),
     642             :                                            INET_PROT_FILE,
     643             :                                            INetURLObject::ENCODE_ALL,
     644             :                                            RTL_TEXTENCODING_UTF8,
     645           0 :                                            INetURLObject::FSYS_DOS);
     646           0 :                         if (!aUri.HasError())
     647             :                         {
     648           0 :                             rBegin = nPos;
     649           0 :                             rEnd = nUriEnd;
     650             :                             return
     651           0 :                                 aUri.GetMainURL(INetURLObject::DECODE_TO_IURI);
     652           0 :                         }
     653             :                     }
     654             :                 }
     655             :             }
     656           0 :             else if ((eStyle & INetURLObject::FSYS_DOS) != 0 && rEnd - nPos >= 2
     657           0 :                      && rText[nPos] == '\\'
     658           0 :                      && rText[nPos + 1] == '\\') // 6th
     659             :             {
     660           0 :                 sal_Int32 i = nPos + 2;
     661           0 :                 sal_uInt32 nLabels = scanDomain(rText, &i, rEnd);
     662           0 :                 if (nLabels >= 1 && i != rEnd && rText[i] == '\\')
     663             :                 {
     664           0 :                     sal_Int32 nUriEnd = ++i;
     665           0 :                     while (i != rEnd
     666           0 :                            && checkWChar(rCharClass, rText, &i, &nUriEnd,
     667           0 :                                          true)) ;
     668           0 :                     if (isBoundary1(rCharClass, rText, nUriEnd, rEnd))
     669             :                     {
     670             :                         INetURLObject aUri(rText.copy(nPos, nUriEnd - nPos),
     671             :                                            INET_PROT_FILE,
     672             :                                            INetURLObject::ENCODE_ALL,
     673             :                                            RTL_TEXTENCODING_UTF8,
     674           0 :                                            INetURLObject::FSYS_DOS);
     675           0 :                         if (!aUri.HasError())
     676             :                         {
     677           0 :                             rBegin = nPos;
     678           0 :                             rEnd = nUriEnd;
     679             :                             return
     680           0 :                                 aUri.GetMainURL(INetURLObject::DECODE_TO_IURI);
     681           0 :                         }
     682             :                     }
     683             :                 }
     684             :             }
     685             :         }
     686           0 :         if (bBoundary2 && INetMIME::isAtomChar(c)) // 5th
     687             :         {
     688           0 :             bool bDot = false;
     689           0 :             for (sal_Int32 i = nPos + 1; i != rEnd; ++i)
     690             :             {
     691           0 :                 sal_Unicode c2 = rText[i];
     692           0 :                 if (INetMIME::isAtomChar(c2))
     693           0 :                     bDot = false;
     694           0 :                 else if (bDot)
     695           0 :                     break;
     696           0 :                 else if (c2 == '.')
     697           0 :                     bDot = true;
     698             :                 else
     699             :                 {
     700           0 :                     if (c2 == '@')
     701             :                     {
     702           0 :                         ++i;
     703           0 :                         sal_uInt32 nLabels = scanDomain(rText, &i, rEnd);
     704           0 :                         if (nLabels >= 1
     705           0 :                             && isBoundary1(rCharClass, rText, i, rEnd))
     706             :                         {
     707             :                             INetURLObject aUri(rText.copy(nPos, i - nPos),
     708             :                                                INET_PROT_MAILTO,
     709           0 :                                                INetURLObject::ENCODE_ALL);
     710           0 :                             if (!aUri.HasError())
     711             :                             {
     712           0 :                                 rBegin = nPos;
     713           0 :                                 rEnd = i;
     714             :                                 return aUri.GetMainURL(
     715           0 :                                            INetURLObject::DECODE_TO_IURI);
     716           0 :                             }
     717             :                         }
     718             :                     }
     719           0 :                     break;
     720             :                 }
     721             :             }
     722             :         }
     723           0 :         bBoundary1 = isBoundary1(rCharClass, rText, nPos, rEnd);
     724           0 :         bBoundary2 = isBoundary2(rCharClass, rText, nPos, rEnd);
     725             :     }
     726           0 :     rBegin = rEnd;
     727           0 :     return OUString();
     728             : }
     729             : 
     730             : 
     731             : //  removePassword
     732             : 
     733             : 
     734           0 : OUString URIHelper::removePassword(OUString const & rURI,
     735             :                                    INetURLObject::EncodeMechanism eEncodeMechanism,
     736             :                                    INetURLObject::DecodeMechanism eDecodeMechanism,
     737             :                                    rtl_TextEncoding eCharset)
     738             : {
     739           0 :     INetURLObject aObj(rURI, eEncodeMechanism, eCharset);
     740           0 :     return aObj.HasError() ?
     741             :                rURI :
     742           0 :                aObj.GetURLNoPass(eDecodeMechanism, eCharset);
     743             : }
     744             : 
     745             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10