1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
20 #include <osl/security.hxx>
21 #include <osl/file.hxx>
22 #include <osl/socket.h>
23 #include <cppuhelper/queryinterface.hxx>
24 #include <comphelper/processfactory.hxx>
25 #include <com/sun/star/beans/PropertyAttribute.hpp>
26 #include <com/sun/star/ucb/FileSystemNotation.hpp>
27 #include <com/sun/star/ucb/IllegalIdentifierException.hpp>
28 #include <cppuhelper/factory.hxx>
29 #include <cppuhelper/supportsservice.hxx>
30 #include "filglob.hxx"
32 #include "filtask.hxx"
36 using namespace fileaccess
;
37 using namespace com::sun::star
;
38 using namespace com::sun::star::uno
;
39 using namespace com::sun::star::lang
;
40 using namespace com::sun::star::beans
;
41 using namespace com::sun::star::ucb
;
42 using namespace com::sun::star::container
;
44 #if OSL_DEBUG_LEVEL > 0
45 #define THROW_WHERE SAL_WHERE
47 #define THROW_WHERE ""
51 extern "C" SAL_DLLPUBLIC_EXPORT
void * ucpfile_component_getFactory(
52 const sal_Char
* pImplName
, void * pServiceManager
, void * )
54 void * pRet
= nullptr;
56 Reference
< XMultiServiceFactory
> xSMgr(
57 static_cast< XMultiServiceFactory
* >( pServiceManager
) );
58 Reference
< XSingleServiceFactory
> xFactory
;
61 // File Content Provider.
64 if ( fileaccess::TaskManager::getImplementationName_static().
65 equalsAscii( pImplName
) )
67 xFactory
= FileProvider::createServiceFactory( xSMgr
);
74 pRet
= xFactory
.get();
80 /****************************************************************************/
86 /****************************************************************************/
87 FileProvider::FileProvider( const Reference
< XComponentContext
>& rxContext
)
88 : m_xContext(rxContext
)
89 , m_FileSystemNotation(FileSystemNotation::UNKNOWN_NOTATION
)
93 FileProvider::~FileProvider()
98 void FileProvider::init()
101 m_pMyShell
.reset( new TaskManager( m_xContext
, this, true ) );
106 FileProvider::initialize(
107 const Sequence
< Any
>& aArguments
)
111 if( aArguments
.hasElements() &&
112 (aArguments
[0] >>= config
) &&
113 config
== "NoConfig" )
114 m_pMyShell
.reset( new TaskManager( m_xContext
, this, false ) );
116 m_pMyShell
.reset( new TaskManager( m_xContext
, this, true ) );
120 // XServiceInfo methods.
122 FileProvider::getImplementationName()
124 return fileaccess::TaskManager::getImplementationName_static();
127 sal_Bool SAL_CALL
FileProvider::supportsService(const OUString
& ServiceName
)
129 return cppu::supportsService(this, ServiceName
);
132 Sequence
< OUString
> SAL_CALL
133 FileProvider::getSupportedServiceNames()
135 return fileaccess::TaskManager::getSupportedServiceNames_static();
138 Reference
< XSingleServiceFactory
>
139 FileProvider::createServiceFactory(
140 const Reference
< XMultiServiceFactory
>& rxServiceMgr
)
142 return cppu::createSingleFactory(
144 fileaccess::TaskManager::getImplementationName_static(),
145 FileProvider::CreateInstance
,
146 fileaccess::TaskManager::getSupportedServiceNames_static() );
149 Reference
< XInterface
> SAL_CALL
150 FileProvider::CreateInstance(
151 const Reference
< XMultiServiceFactory
>& xMultiServiceFactory
)
153 XServiceInfo
* xP
= new FileProvider(comphelper::getComponentContext(xMultiServiceFactory
));
154 return Reference
< XInterface
>::query( xP
);
161 Reference
< XContent
> SAL_CALL
162 FileProvider::queryContent(
163 const Reference
< XContentIdentifier
>& xIdentifier
)
167 bool err
= fileaccess::TaskManager::getUnqFromUrl( xIdentifier
->getContentIdentifier(),
171 throw IllegalIdentifierException( THROW_WHERE
);
173 return Reference
< XContent
>( new BaseContent( m_pMyShell
.get(), xIdentifier
, aUnc
) );
178 FileProvider::compareContentIds(
179 const Reference
< XContentIdentifier
>& Id1
,
180 const Reference
< XContentIdentifier
>& Id2
)
183 OUString aUrl1
= Id1
->getContentIdentifier();
184 OUString aUrl2
= Id2
->getContentIdentifier();
186 sal_Int32 iComp
= aUrl1
.compareTo( aUrl2
);
190 OUString aPath1
, aPath2
;
192 fileaccess::TaskManager::getUnqFromUrl( aUrl1
, aPath1
);
193 fileaccess::TaskManager::getUnqFromUrl( aUrl2
, aPath2
);
195 osl::FileBase::RC error
;
196 osl::DirectoryItem aItem1
, aItem2
;
198 error
= osl::DirectoryItem::get( aPath1
, aItem1
);
199 if ( error
== osl::FileBase::E_None
)
200 error
= osl::DirectoryItem::get( aPath2
, aItem2
);
202 if ( error
!= osl::FileBase::E_None
)
205 osl::FileStatus
aStatus1( osl_FileStatus_Mask_FileURL
);
206 osl::FileStatus
aStatus2( osl_FileStatus_Mask_FileURL
);
207 error
= aItem1
.getFileStatus( aStatus1
);
208 if ( error
== osl::FileBase::E_None
)
209 error
= aItem2
.getFileStatus( aStatus2
);
211 if ( error
== osl::FileBase::E_None
)
213 iComp
= aStatus1
.getFileURL().compareTo( aStatus2
.getFileURL() );
215 // Quick hack for Windows to threat all file systems as case insensitive
219 error
= osl::FileBase::getSystemPathFromFileURL( aStatus1
.getFileURL(), aPath1
);
220 if ( error
== osl::FileBase::E_None
)
221 error
= osl::FileBase::getSystemPathFromFileURL( aStatus2
.getFileURL(), aPath2
);
223 if ( error
== osl::FileBase::E_None
)
224 iComp
= aPath1
.compareToIgnoreAsciiCase( aPath2
);
234 Reference
< XContentIdentifier
> SAL_CALL
235 FileProvider::createContentIdentifier(
236 const OUString
& ContentId
)
239 FileContentIdentifier
* p
= new FileContentIdentifier( ContentId
,false );
240 return Reference
< XContentIdentifier
>( p
);
244 //XPropertySetInfoImpl
246 class XPropertySetInfoImpl2
247 : public cppu::OWeakObject
,
248 public XPropertySetInfo
251 XPropertySetInfoImpl2();
255 queryInterface( const Type
& aType
) override
;
257 virtual void SAL_CALL
261 virtual void SAL_CALL
266 virtual Sequence
< Property
> SAL_CALL
267 getProperties() override
;
269 virtual Property SAL_CALL
270 getPropertyByName( const OUString
& aName
) override
;
272 virtual sal_Bool SAL_CALL
273 hasPropertyByName( const OUString
& Name
) override
;
277 Sequence
< Property
> m_seq
;
281 XPropertySetInfoImpl2::XPropertySetInfoImpl2()
284 m_seq
[0] = Property( "HostName",
286 cppu::UnoType
<OUString
>::get(),
287 PropertyAttribute::READONLY
);
289 m_seq
[1] = Property( "HomeDirectory",
291 cppu::UnoType
<OUString
>::get(),
292 PropertyAttribute::READONLY
);
294 m_seq
[2] = Property( "FileSystemNotation",
296 cppu::UnoType
<sal_Int32
>::get(),
297 PropertyAttribute::READONLY
);
301 XPropertySetInfoImpl2::acquire()
304 OWeakObject::acquire();
309 XPropertySetInfoImpl2::release()
312 OWeakObject::release();
317 XPropertySetInfoImpl2::queryInterface( const Type
& rType
)
319 Any aRet
= cppu::queryInterface( rType
,
320 static_cast< XPropertySetInfo
* >(this) );
321 return aRet
.hasValue() ? aRet
: OWeakObject::queryInterface( rType
);
326 XPropertySetInfoImpl2::getPropertyByName( const OUString
& aName
)
328 auto pProp
= std::find_if(m_seq
.begin(), m_seq
.end(),
329 [&aName
](const Property
& rProp
) { return rProp
.Name
== aName
; });
330 if (pProp
!= m_seq
.end())
333 throw UnknownPropertyException( aName
);
337 Sequence
< Property
> SAL_CALL
338 XPropertySetInfoImpl2::getProperties()
345 XPropertySetInfoImpl2::hasPropertyByName(
346 const OUString
& aName
)
348 return std::any_of(m_seq
.begin(), m_seq
.end(),
349 [&aName
](const Property
& rProp
) { return rProp
.Name
== aName
; });
353 void FileProvider::initProperties()
355 osl::MutexGuard
aGuard( m_aMutex
);
356 if( ! m_xPropertySetInfo
.is() )
358 osl_getLocalHostname( &m_HostName
.pData
);
361 m_FileSystemNotation
= FileSystemNotation::UNIX_NOTATION
;
363 m_FileSystemNotation
= FileSystemNotation::DOS_NOTATION
;
365 m_FileSystemNotation
= FileSystemNotation::UNKNOWN_NOTATION
;
367 osl::Security aSecurity
;
368 aSecurity
.getHomeDir( m_HomeDirectory
);
370 // static const sal_Int32 UNKNOWN_NOTATION = (sal_Int32)0;
371 // static const sal_Int32 UNIX_NOTATION = (sal_Int32)1;
372 // static const sal_Int32 DOS_NOTATION = (sal_Int32)2;
373 // static const sal_Int32 MAC_NOTATION = (sal_Int32)3;
375 XPropertySetInfoImpl2
* p
= new XPropertySetInfoImpl2();
376 m_xPropertySetInfo
.set( p
);
383 Reference
< XPropertySetInfo
> SAL_CALL
384 FileProvider::getPropertySetInfo( )
387 return m_xPropertySetInfo
;
392 FileProvider::setPropertyValue( const OUString
& aPropertyName
,
395 if( !(aPropertyName
== "FileSystemNotation" ||
396 aPropertyName
== "HomeDirectory" ||
397 aPropertyName
== "HostName") )
398 throw UnknownPropertyException( aPropertyName
);
403 FileProvider::getPropertyValue(
404 const OUString
& aPropertyName
)
407 if( aPropertyName
== "FileSystemNotation" )
409 return Any(m_FileSystemNotation
);
411 else if( aPropertyName
== "HomeDirectory" )
413 return Any(m_HomeDirectory
);
415 else if( aPropertyName
== "HostName" )
417 return Any(m_HostName
);
420 throw UnknownPropertyException( aPropertyName
);
425 FileProvider::addPropertyChangeListener(
427 const Reference
< XPropertyChangeListener
>& )
433 FileProvider::removePropertyChangeListener(
435 const Reference
< XPropertyChangeListener
>& )
440 FileProvider::addVetoableChangeListener(
442 const Reference
< XVetoableChangeListener
>& )
448 FileProvider::removeVetoableChangeListener(
450 const Reference
< XVetoableChangeListener
>& )
455 // XFileIdentifierConverter
458 FileProvider::getFileProviderLocality( const OUString
& BaseURL
)
460 // If the base URL is a 'file' URL, return 10 (very 'local'), otherwise
461 // return -1 (mismatch). What is missing is a fast comparison to ASCII,
463 return BaseURL
.getLength() >= 5
464 && (BaseURL
[0] == 'F' || BaseURL
[0] == 'f')
465 && (BaseURL
[1] == 'I' || BaseURL
[1] == 'i')
466 && (BaseURL
[2] == 'L' || BaseURL
[2] == 'l')
467 && (BaseURL
[3] == 'E' || BaseURL
[3] == 'e')
468 && BaseURL
[4] == ':' ?
472 OUString SAL_CALL
FileProvider::getFileURLFromSystemPath( const OUString
&,
473 const OUString
& SystemPath
)
475 OUString aNormalizedPath
;
476 if ( osl::FileBase::getFileURLFromSystemPath( SystemPath
,aNormalizedPath
) != osl::FileBase::E_None
)
479 return aNormalizedPath
;
482 OUString SAL_CALL
FileProvider::getSystemPathFromFileURL( const OUString
& URL
)
484 OUString aSystemPath
;
485 if (osl::FileBase::getSystemPathFromFileURL( URL
,aSystemPath
) != osl::FileBase::E_None
)
491 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */