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 .
19 #ifndef INCLUDED_COM_SUN_STAR_UNO_REFERENCE_H
20 #define INCLUDED_COM_SUN_STAR_UNO_REFERENCE_H
22 #include "sal/config.h"
27 #if defined LIBO_INTERNAL_ONLY
28 #include <type_traits>
31 #include "rtl/alloc.h"
42 class RuntimeException
;
47 /** Enum defining UNO_REF_NO_ACQUIRE for setting reference without acquiring a given interface.
48 Deprecated, please use SAL_NO_ACQUIRE.
51 enum UnoReference_NoAcquire
53 /** This enum value can be used for creating a reference granting a given interface,
54 i.e. transferring ownership to it.
59 /** This base class serves as a base class for all template reference classes and
60 has been introduced due to compiler problems with templated operators ==, =!.
65 /** the interface pointer
67 XInterface
* _pInterface
;
69 /** Queries given interface for type rType.
71 @param pInterface interface pointer
72 @param rType interface type
73 @return interface of demanded type (may be null)
75 inline static XInterface
* SAL_CALL
iquery( XInterface
* pInterface
, const Type
& rType
);
76 /** Queries given interface for type rType.
77 Throws a RuntimeException if the demanded interface cannot be queried.
79 @param pInterface interface pointer
80 @param rType interface type
81 @return interface of demanded type
83 inline static XInterface
* SAL_CALL
iquery_throw( XInterface
* pInterface
, const Type
& rType
);
86 /** Gets interface pointer. This call does not acquire the interface.
88 @return UNacquired interface pointer
90 XInterface
* SAL_CALL
get() const
91 { return _pInterface
; }
93 /** Checks if reference is null.
95 @return true if reference acquires an interface, i.e. true if it is not null
97 bool SAL_CALL
is() const
98 { return (NULL
!= _pInterface
); }
100 #if defined LIBO_INTERNAL_ONLY
101 /** Checks if reference is null.
103 @return true if reference acquires an interface, i.e. true if it is not null
105 explicit operator bool() const
109 /** Equality operator: compares two interfaces
110 Checks if both references are null or refer to the same object.
112 @param pInterface another interface
113 @return true if both references are null or refer to the same object, false otherwise
115 inline bool SAL_CALL
operator == ( XInterface
* pInterface
) const;
116 /** Inequality operator: compares two interfaces
117 Checks if both references are null or refer to the same object.
119 @param pInterface another interface
120 @return false if both references are null or refer to the same object, true otherwise
122 inline bool SAL_CALL
operator != ( XInterface
* pInterface
) const;
124 /** Equality operator: compares two interfaces
125 Checks if both references are null or refer to the same object.
127 @param rRef another reference
128 @return true if both references are null or refer to the same object, false otherwise
130 inline bool SAL_CALL
operator == ( const BaseReference
& rRef
) const;
131 /** Inequality operator: compares two interfaces
132 Checks if both references are null or refer to the same object.
134 @param rRef another reference
135 @return false if both references are null or refer to the same object, true otherwise
137 inline bool SAL_CALL
operator != ( const BaseReference
& rRef
) const;
139 /** Needed by some STL containers.
141 @param rRef another reference
142 @return true, if this reference is less than rRef
144 inline bool SAL_CALL
operator < ( const BaseReference
& rRef
) const;
147 /** Enum defining UNO_QUERY for implicit interface query.
149 enum UnoReference_Query
151 /** This enum value can be used for implicit interface query.
155 /** Enum defining UNO_QUERY_THROW for implicit interface query.
156 If the demanded interface is unavailable, then a RuntimeException is thrown.
158 enum UnoReference_QueryThrow
160 /** This enum value can be used for implicit interface query.
164 /** Enum defining UNO_SET_THROW for throwing if attempts are made to assign a null
169 enum UnoReference_SetThrow
174 /** Template reference class for interface type derived from BaseReference.
175 A special constructor given the UNO_QUERY identifier queries interfaces
178 template< class interface_type
>
179 class SAL_DLLPUBLIC_RTTI Reference
: public BaseReference
181 /** Queries given interface for type interface_type.
183 @param pInterface interface pointer
184 @return interface of demanded type (may be null)
186 inline static XInterface
* SAL_CALL
iquery( XInterface
* pInterface
);
187 /** Queries given interface for type interface_type.
188 Throws a RuntimeException if the demanded interface cannot be queried.
190 @param pInterface interface pointer
191 @return interface of demanded type
193 inline static XInterface
* SAL_CALL
iquery_throw( XInterface
* pInterface
);
194 /** Returns the given interface if it is not <NULL/>, throws a RuntimeException otherwise.
196 @param pInterface interface pointer
199 inline static interface_type
* SAL_CALL
iset_throw( interface_type
* pInterface
);
201 /** Cast from an "interface pointer" (e.g., BaseReference::_pInterface) to a
202 pointer to this interface_type.
204 To work around ambiguities in the case of multiple-inheritance interface
205 types (which inherit XInterface more than once), use reinterpret_cast
206 (resp. a sequence of two static_casts, to avoid warnings about
207 reinterpret_cast used between related classes) to switch from a pointer
208 to XInterface to a pointer to this derived interface_type. In
209 principle, this is not guaranteed to work. In practice, it seems to
210 work on all supported platforms.
212 static interface_type
* castFromXInterface(XInterface
* p
) {
213 return static_cast< interface_type
* >(static_cast< void * >(p
));
216 /** Cast from a pointer to this interface_type to an "interface pointer"
217 (e.g., BaseReference::_pInterface).
219 To work around ambiguities in the case of multiple-inheritance interface
220 types (which inherit XInterface more than once), use reinterpret_cast
221 (resp. a sequence of two static_casts, to avoid warnings about
222 reinterpret_cast used between related classes) to switch from a pointer
223 to this derived interface_type to a pointer to XInterface. In
224 principle, this is not guaranteed to work. In practice, it seems to
225 work on all supported platforms.
227 static XInterface
* castToXInterface(interface_type
* p
) {
228 return static_cast< XInterface
* >(static_cast< void * >(p
));
233 // these are here to force memory de/allocation to sal lib.
234 static void * SAL_CALL
operator new ( ::size_t nSize
)
235 { return ::rtl_allocateMemory( nSize
); }
236 static void SAL_CALL
operator delete ( void * pMem
)
237 { ::rtl_freeMemory( pMem
); }
238 static void * SAL_CALL
operator new ( ::size_t, void * pMem
)
240 static void SAL_CALL
operator delete ( void *, void * )
244 /** Destructor: Releases interface if set.
246 inline ~Reference() COVERITY_NOEXCEPT_FALSE
;
248 /** Default Constructor: Sets null reference.
252 /** Copy constructor: Copies interface reference.
254 @param rRef another reference
256 inline Reference( const Reference
< interface_type
> & rRef
);
258 #if defined LIBO_INTERNAL_ONLY
261 @param rRef another reference
263 inline Reference( Reference
< interface_type
> && rRef
) noexcept
;
265 /** Up-casting conversion constructor: Copies interface reference.
267 Does not work for up-casts to ambiguous bases. For the special case of
268 up-casting to Reference< XInterface >, see the corresponding conversion
271 @param rRef another reference
273 template< class derived_type
>
275 const Reference
< derived_type
> & rRef
,
277 std::is_base_of_v
<interface_type
, derived_type
>
278 && !std::is_same_v
<interface_type
, XInterface
>, void *> = nullptr);
281 /** Constructor: Sets given interface pointer.
283 @param pInterface an interface pointer
285 inline Reference( interface_type
* pInterface
);
287 /** Constructor: Sets given interface pointer without acquiring it.
289 @param pInterface another reference
290 @param dummy SAL_NO_ACQUIRE to force obvious distinction to other constructors
292 inline Reference( interface_type
* pInterface
, __sal_NoAcquire dummy
);
293 /** Constructor: Sets given interface pointer without acquiring it.
294 Deprecated, please use SAL_NO_ACQUIRE version.
297 @param pInterface another reference
298 @param dummy UNO_REF_NO_ACQUIRE to force obvious distinction to other constructors
300 inline SAL_DEPRECATED("use SAL_NO_ACQUIRE version") Reference( interface_type
* pInterface
, UnoReference_NoAcquire dummy
);
302 /** Constructor: Queries given interface for reference interface type (interface_type).
304 @param rRef another reference
305 @param dummy UNO_QUERY to force obvious distinction to other constructors
307 inline Reference( const BaseReference
& rRef
, UnoReference_Query dummy
);
308 /** Constructor: Queries given interface for reference interface type (interface_type).
310 @param pInterface an interface pointer
311 @param dummy UNO_QUERY to force obvious distinction to other constructors
313 inline Reference( XInterface
* pInterface
, UnoReference_Query dummy
);
314 /** Constructor: Queries given any for reference interface type (interface_type).
317 @param dummy UNO_QUERY to force obvious distinction to other constructors
319 inline Reference( const Any
& rAny
, UnoReference_Query dummy
);
320 /** Constructor: Queries given interface for reference interface type (interface_type).
321 Throws a RuntimeException if the demanded interface cannot be queried.
323 @param rRef another reference
324 @param dummy UNO_QUERY_THROW to force obvious distinction
325 to other constructors
327 inline Reference( const BaseReference
& rRef
, UnoReference_QueryThrow dummy
);
328 #ifdef LIBO_INTERNAL_ONLY
330 Prevent code from calling the QUERY_THROW constructor, when they meant to use the SET_THROW constructor.
332 Reference( const Reference
< interface_type
> & rRef
, UnoReference_QueryThrow dummy
) = delete;
334 /** Constructor: Queries given interface for reference interface type (interface_type).
335 Throws a RuntimeException if the demanded interface cannot be queried.
337 @param pInterface an interface pointer
338 @param dummy UNO_QUERY_THROW to force obvious distinction
339 to other constructors
341 inline Reference( XInterface
* pInterface
, UnoReference_QueryThrow dummy
);
342 /** Constructor: Queries given any for reference interface type (interface_type).
343 Throws a RuntimeException if the demanded interface cannot be queried.
346 @param dummy UNO_QUERY_THROW to force obvious distinction
347 to other constructors
349 inline Reference( const Any
& rAny
, UnoReference_QueryThrow dummy
);
350 /** Constructor: assigns from the given interface of the same type. Throws a RuntimeException
351 if the source interface is NULL.
353 @param rRef another interface reference of the same type
354 @param dummy UNO_SET_THROW to distinguish from default copy constructor
358 inline Reference( const Reference
< interface_type
> & rRef
, UnoReference_SetThrow dummy
);
359 /** Constructor: assigns from the given interface of the same type. Throws a RuntimeException
360 if the source interface is NULL.
362 @param pInterface an interface pointer
363 @param dummy UNO_SET_THROW to distinguish from default assignment constructor
367 inline Reference( interface_type
* pInterface
, UnoReference_SetThrow dummy
);
369 /** Cast operator to Reference< XInterface >: Reference objects are binary compatible and
370 any interface must be derived from com.sun.star.uno.XInterface.
371 This a useful direct cast possibility.
373 SAL_CALL
operator const Reference
< XInterface
> & () const
374 { return * reinterpret_cast< const Reference
< XInterface
> * >( this ); }
376 /** Dereference operator: Used to call interface methods.
378 @return UNacquired interface pointer
380 interface_type
* SAL_CALL
operator -> () const {
381 assert(_pInterface
!= NULL
);
382 return castFromXInterface(_pInterface
);
385 /** Indirection operator.
387 @since LibreOffice 6.3
388 @return UNacquired interface reference
390 interface_type
& SAL_CALL
operator * () const {
391 assert(_pInterface
!= NULL
);
392 return *castFromXInterface(_pInterface
);
395 /** Gets interface pointer. This call does not acquire the interface.
397 @return UNacquired interface pointer
399 interface_type
* SAL_CALL
get() const
400 { return castFromXInterface(_pInterface
); }
402 /** Clears reference, i.e. releases interface. Reference is null after clear() call.
404 inline void SAL_CALL
clear();
406 /** Sets the given interface. An interface already set will be released.
408 @param rRef another reference
409 @return true, if non-null interface was set
411 inline bool SAL_CALL
set( const Reference
< interface_type
> & rRef
);
412 /** Sets the given interface. An interface already set will be released.
414 @param pInterface another interface
415 @return true, if non-null interface was set
417 inline bool SAL_CALL
set( interface_type
* pInterface
);
419 /** Sets interface pointer without acquiring it. An interface already set will be released.
421 @param pInterface an interface pointer
422 @param dummy SAL_NO_ACQUIRE to force obvious distinction to set methods
423 @return true, if non-null interface was set
425 inline bool SAL_CALL
set( interface_type
* pInterface
, __sal_NoAcquire dummy
);
426 /** Sets interface pointer without acquiring it. An interface already set will be released.
427 Deprecated, please use SAL_NO_ACQUIRE version.
430 @param pInterface an interface pointer
431 @param dummy UNO_REF_NO_ACQUIRE to force obvious distinction to set methods
432 @return true, if non-null interface was set
434 inline SAL_DEPRECATED("use SAL_NO_ACQUIRE version") bool SAL_CALL
set( interface_type
* pInterface
, UnoReference_NoAcquire dummy
);
436 /** Queries given interface for reference interface type (interface_type) and sets it.
437 An interface already set will be released.
439 @param pInterface an interface pointer
440 @param dummy UNO_QUERY to force obvious distinction to set methods
441 @return true, if non-null interface was set
443 inline bool SAL_CALL
set( XInterface
* pInterface
, UnoReference_Query dummy
);
444 /** Queries given interface for reference interface type (interface_type) and sets it.
445 An interface already set will be released.
447 @param rRef another reference
448 @param dummy UNO_QUERY to force obvious distinction to set methods
449 @return true, if non-null interface was set
451 inline bool SAL_CALL
set( const BaseReference
& rRef
, UnoReference_Query dummy
);
453 /** Queries given any for reference interface type (interface_type)
454 and sets it. An interface already set will be released.
457 an Any containing an interface
459 UNO_QUERY to force obvious distinction
462 true, if non-null interface was set
464 inline bool set( Any
const & rAny
, UnoReference_Query dummy
);
466 /** Queries given interface for reference interface type (interface_type) and sets it.
467 An interface already set will be released.
468 Throws a RuntimeException if the demanded interface cannot be set.
470 @param pInterface an interface pointer
471 @param dummy UNO_QUERY_THROW to force obvious distinction
474 inline void SAL_CALL
set( XInterface
* pInterface
, UnoReference_QueryThrow dummy
);
475 /** Queries given interface for reference interface type (interface_type) and sets it.
476 An interface already set will be released.
477 Throws a RuntimeException if the demanded interface cannot be set.
479 @param rRef another reference
480 @param dummy UNO_QUERY_THROW to force obvious distinction
483 inline void SAL_CALL
set( const BaseReference
& rRef
, UnoReference_QueryThrow dummy
);
484 #ifdef LIBO_INTERNAL_ONLY
486 Prevent code from calling the QUERY_THROW version, when they meant to use the SET_THROW version.
488 void set( const Reference
< interface_type
> & rRef
, UnoReference_QueryThrow dummy
) = delete;
491 /** Queries given any for reference interface type (interface_type) and
492 sets it. An interface already set will be released.
493 Throws a RuntimeException if the demanded interface cannot be set.
496 an Any containing an interface
498 UNO_QUERY_THROW to force obvious distinction to set methods
500 inline void set( Any
const & rAny
, UnoReference_QueryThrow dummy
);
501 /** sets the given interface
502 An interface already set will be released.
503 Throws a RuntimeException if the source interface is @b NULL.
505 @param pInterface an interface pointer
506 @param dummy UNO_SET_THROW to force obvious distinction to other set methods
510 inline void SAL_CALL
set( interface_type
* pInterface
, UnoReference_SetThrow dummy
);
511 /** sets the given interface
512 An interface already set will be released.
513 Throws a RuntimeException if the source interface is @b NULL.
515 @param rRef an interface reference
516 @param dummy UNO_SET_THROW to force obvious distinction to other set methods
520 inline void SAL_CALL
set( const Reference
< interface_type
> & rRef
, UnoReference_SetThrow dummy
);
523 /** Assignment operator: Acquires given interface pointer and sets reference.
524 An interface already set will be released.
526 @param pInterface an interface pointer
527 @return this reference
529 inline Reference
< interface_type
> & SAL_CALL
operator = ( interface_type
* pInterface
);
530 /** Assignment operator: Acquires given interface reference and sets reference.
531 An interface already set will be released.
533 @param rRef an interface reference
534 @return this reference
536 inline Reference
< interface_type
> & SAL_CALL
operator = ( const Reference
< interface_type
> & rRef
);
537 #if defined LIBO_INTERNAL_ONLY
538 /** Assignment move operator: Acquires given interface reference and sets reference.
539 An interface already set will be released.
541 @param rRef an interface reference
542 @return this reference
544 inline Reference
< interface_type
> & SAL_CALL
operator = ( Reference
< interface_type
> && rRef
) noexcept
;
546 /** Queries given interface reference for type interface_type.
548 @param rRef interface reference
549 @return interface reference of demanded type (may be null)
551 SAL_WARN_UNUSED_RESULT
inline static Reference
< interface_type
> SAL_CALL
query( const BaseReference
& rRef
);
552 /** Queries given interface for type interface_type.
554 @param pInterface interface pointer
555 @return interface reference of demanded type (may be null)
557 SAL_WARN_UNUSED_RESULT
inline static Reference
< interface_type
> SAL_CALL
query( XInterface
* pInterface
);
567 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */