1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: acceptor.cxx,v $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_io.hxx"
33 #include <osl/mutex.hxx>
35 #include <uno/mapping.hxx>
37 #include <cppuhelper/factory.hxx>
38 #include <cppuhelper/implbase2.hxx>
39 #include <cppuhelper/implementationentry.hxx>
40 #include "cppuhelper/unourl.hxx"
41 #include "rtl/malformeduriexception.hxx"
43 #include <com/sun/star/connection/XAcceptor.hpp>
44 #include <com/sun/star/lang/XServiceInfo.hpp>
46 #include "acceptor.hxx"
48 #define IMPLEMENTATION_NAME "com.sun.star.comp.io.Acceptor"
49 #define SERVICE_NAME "com.sun.star.connection.Acceptor"
51 using namespace ::osl
;
52 using namespace ::rtl
;
53 using namespace ::cppu
;
54 using namespace ::com::sun::star::uno
;
55 using namespace ::com::sun::star::lang
;
56 using namespace ::com::sun::star::registry
;
57 using namespace ::com::sun::star::connection
;
61 rtl_StandardModuleCount g_moduleCount
= MODULE_COUNT_INIT
;
63 class OAcceptor
: public WeakImplHelper2
< XAcceptor
, XServiceInfo
>
66 OAcceptor(const Reference
< XComponentContext
> & xCtx
);
70 virtual Reference
< XConnection
> SAL_CALL
accept( const OUString
& sConnectionDescription
)
71 throw( AlreadyAcceptingException
,
72 ConnectionSetupException
,
73 IllegalArgumentException
,
75 virtual void SAL_CALL
stopAccepting( ) throw( RuntimeException
);
77 public: // XServiceInfo
78 virtual OUString SAL_CALL
getImplementationName() throw();
79 virtual Sequence
< OUString
> SAL_CALL
getSupportedServiceNames(void) throw();
80 virtual sal_Bool SAL_CALL
supportsService(const OUString
& ServiceName
) throw();
83 PipeAcceptor
*m_pPipe
;
84 SocketAcceptor
*m_pSocket
;
86 OUString m_sLastDescription
;
89 Reference
< XMultiComponentFactory
> _xSMgr
;
90 Reference
< XComponentContext
> _xCtx
;
91 Reference
<XAcceptor
> _xAcceptor
;
95 OAcceptor::OAcceptor( const Reference
< XComponentContext
> & xCtx
)
98 , m_bInAccept( sal_False
)
99 , _xSMgr( xCtx
->getServiceManager() )
102 g_moduleCount
.modCnt
.acquire( &g_moduleCount
.modCnt
);
105 OAcceptor::~OAcceptor()
115 g_moduleCount
.modCnt
.release( &g_moduleCount
.modCnt
);
120 BeingInAccept( sal_Bool
*pFlag
,const OUString
& sConnectionDescription
) throw( AlreadyAcceptingException
)
125 OUString
sMessage( RTL_CONSTASCII_USTRINGPARAM( "AlreadyAcceptingException :" ) );
126 sMessage
+= sConnectionDescription
;
127 throw AlreadyAcceptingException( sMessage
, Reference
< XInterface
> () );
133 *m_pFlag
= sal_False
;
138 Reference
< XConnection
> OAcceptor::accept( const OUString
&sConnectionDescription
)
139 throw( AlreadyAcceptingException
,
140 ConnectionSetupException
,
141 IllegalArgumentException
,
147 sConnectionDescription
, RTL_TEXTENCODING_ASCII_US
).getStr());
148 // if there is a thread alread accepting in this object, throw an exception.
149 struct BeingInAccept
guard( &m_bInAccept
, sConnectionDescription
);
151 Reference
< XConnection
> r
;
152 if( m_sLastDescription
.getLength() &&
153 m_sLastDescription
!= sConnectionDescription
)
155 // instantiate another acceptor for different ports
156 OUString sMessage
= OUString( RTL_CONSTASCII_USTRINGPARAM(
157 "acceptor::accept called multiple times with different conncetion strings\n" ) );
158 throw ConnectionSetupException( sMessage
, Reference
< XInterface
> () );
161 if( ! m_sLastDescription
.getLength() )
163 // setup the acceptor
166 cppu::UnoUrlDescriptor
aDesc(sConnectionDescription
);
167 if (aDesc
.getName().equalsAsciiL(
168 RTL_CONSTASCII_STRINGPARAM("pipe")))
172 rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(
175 m_pPipe
= new PipeAcceptor(aName
, sConnectionDescription
);
184 MutexGuard
g( m_mutex
);
191 else if (aDesc
.getName().equalsAsciiL(
192 RTL_CONSTASCII_STRINGPARAM("socket")))
195 if (aDesc
.hasParameter(
196 rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("host"))))
197 aHost
= aDesc
.getParameter(
198 rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("host")));
200 aHost
= rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(
202 sal_uInt16 nPort
= static_cast< sal_uInt16
>(
204 rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("port"))).
207 = aDesc
.getParameter(
208 rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(
209 "tcpnodelay"))).toInt32() != 0;
211 m_pSocket
= new SocketAcceptor(
212 aHost
, nPort
, bTcpNoDelay
, sConnectionDescription
);
221 MutexGuard
g( m_mutex
);
230 OUString delegatee
= OUString(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.connection.Acceptor."));
231 delegatee
+= aDesc
.getName();
234 "trying to get service %s\n",
236 delegatee
, RTL_TEXTENCODING_ASCII_US
).getStr());
237 _xAcceptor
= Reference
<XAcceptor
>(
238 _xSMgr
->createInstanceWithContext(delegatee
, _xCtx
), UNO_QUERY
);
242 OUString
message(RTL_CONSTASCII_USTRINGPARAM("Acceptor: unknown delegatee "));
243 message
+= delegatee
;
245 throw ConnectionSetupException(message
, Reference
<XInterface
>());
249 catch (rtl::MalformedUriException
& rEx
)
251 throw IllegalArgumentException(
253 Reference
< XInterface
> (),
256 m_sLastDescription
= sConnectionDescription
;
261 r
= m_pPipe
->accept();
265 r
= m_pSocket
->accept();
269 r
= _xAcceptor
->accept(sConnectionDescription
);
275 void SAL_CALL
OAcceptor::stopAccepting( ) throw( RuntimeException
)
277 MutexGuard
guard( m_mutex
);
281 m_pPipe
->stopAccepting();
283 else if ( m_pSocket
)
285 m_pSocket
->stopAccepting();
287 else if( _xAcceptor
.is() )
289 _xAcceptor
->stopAccepting();
294 OUString
acceptor_getImplementationName()
296 return OUString( RTL_CONSTASCII_USTRINGPARAM( IMPLEMENTATION_NAME
) );
299 Reference
< XInterface
> SAL_CALL
acceptor_CreateInstance( const Reference
< XComponentContext
> & xCtx
)
301 return Reference
< XInterface
>( ( OWeakObject
* ) new OAcceptor(xCtx
) );
304 Sequence
< OUString
> acceptor_getSupportedServiceNames()
306 static Sequence
< OUString
> *pNames
= 0;
309 MutexGuard
guard( Mutex::getGlobalMutex() );
312 static Sequence
< OUString
> seqNames(1);
313 seqNames
.getArray()[0] = OUString::createFromAscii( SERVICE_NAME
);
320 OUString
OAcceptor::getImplementationName() throw()
322 return acceptor_getImplementationName();
325 sal_Bool
OAcceptor::supportsService(const OUString
& ServiceName
) throw()
327 Sequence
< OUString
> aSNL
= getSupportedServiceNames();
328 const OUString
* pArray
= aSNL
.getConstArray();
330 for( sal_Int32 i
= 0; i
< aSNL
.getLength(); i
++ )
331 if( pArray
[i
] == ServiceName
)
337 Sequence
< OUString
> OAcceptor::getSupportedServiceNames(void) throw()
339 return acceptor_getSupportedServiceNames();
345 using namespace io_acceptor
;
347 static struct ImplementationEntry g_entries
[] =
350 acceptor_CreateInstance
, acceptor_getImplementationName
,
351 acceptor_getSupportedServiceNames
, createSingleComponentFactory
,
352 &g_moduleCount
.modCnt
, 0
360 sal_Bool SAL_CALL
component_canUnload( TimeValue
*pTime
)
362 return g_moduleCount
.canUnload( &g_moduleCount
, pTime
);
365 //==================================================================================================
366 void SAL_CALL
component_getImplementationEnvironment(
367 const sal_Char
** ppEnvTypeName
, uno_Environment
** )
369 *ppEnvTypeName
= CPPU_CURRENT_LANGUAGE_BINDING_NAME
;
371 //==================================================================================================
372 sal_Bool SAL_CALL
component_writeInfo(
373 void * pServiceManager
, void * pRegistryKey
)
375 return component_writeInfoHelper( pServiceManager
, pRegistryKey
, g_entries
);
377 //==================================================================================================
378 void * SAL_CALL
component_getFactory(
379 const sal_Char
* pImplName
, void * pServiceManager
, void * pRegistryKey
)
381 return component_getFactoryHelper( pImplName
, pServiceManager
, pRegistryKey
, g_entries
);