Version 6.4.0.3, tag libreoffice-6.4.0.3
[LibreOffice.git] / testtools / source / bridgetest / bridgetest.cxx
blob535d8e1fa73c5eee19e24175b56017301635e1be
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
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 .
21 #include <stdio.h>
22 #include <string.h>
23 #include <o3tl/any.hxx>
24 #include <osl/diagnose.h>
25 #include <osl/diagnose.hxx>
26 #include <osl/time.h>
27 #include <sal/types.h>
28 #include <typelib/typedescription.hxx>
29 #include <uno/dispatcher.hxx>
30 #include <uno/lbnames.h>
31 #include <uno/mapping.hxx>
32 #include <uno/data.h>
33 #include <uno/environment.hxx>
35 #include <cppuhelper/factory.hxx>
36 #include <cppuhelper/implbase.hxx>
37 #include <cppuhelper/supportsservice.hxx>
39 #include <com/sun/star/lang/XServiceInfo.hpp>
40 #include <com/sun/star/lang/XComponent.hpp>
41 #include <com/sun/star/lang/XMain.hpp>
42 #include <com/sun/star/bridge/UnoUrlResolver.hpp>
43 #include <com/sun/star/bridge/XUnoUrlResolver.hpp>
44 #include <com/sun/star/uno/RuntimeException.hpp>
45 #include <com/sun/star/uno/Type.hxx>
47 #include <test/testtools/bridgetest/BadConstructorArguments.hpp>
48 #include <test/testtools/bridgetest/TestPolyStruct.hpp>
49 #include <test/testtools/bridgetest/XBridgeTest.hpp>
50 #include <test/testtools/bridgetest/XBridgeTest2.hpp>
51 #include <test/testtools/bridgetest/XMulti.hpp>
53 #include "currentcontextchecker.hxx"
54 #include "multi.hxx"
55 #include <memory>
57 using namespace osl;
58 using namespace cppu;
59 using namespace com::sun::star::uno;
60 using namespace com::sun::star::lang;
61 using namespace com::sun::star::registry;
62 using namespace com::sun::star::bridge;
63 using namespace test::testtools::bridgetest;
66 #define SERVICENAME "com.sun.star.test.bridge.BridgeTest"
67 #define IMPLNAME "com.sun.star.comp.bridge.BridgeTest"
69 #define STRING_TEST_CONSTANT "\" paco\' chorizo\\\' \"\'"
71 namespace bridge_test
73 template<typename T, typename U = T>
74 static Sequence<T> cloneSequence(const Sequence<T>& val);
77 static Sequence< OUString > getSupportedServiceNames()
79 return { SERVICENAME };
82 static bool check( bool b , char const * message )
84 if ( ! b )
85 fprintf( stderr, "%s failed\n" , message );
86 return b;
89 namespace {
91 bool checkEmpty(OUString const & string, char const * message) {
92 bool ok = string.isEmpty();
93 if (!ok) {
94 fprintf(
95 stderr, "%s failed: %s\n", message,
96 OUStringToOString(string, RTL_TEXTENCODING_UTF8).getStr());
98 return ok;
104 class TestBridgeImpl : public osl::DebugBase<TestBridgeImpl>,
105 public WeakImplHelper< XMain, XServiceInfo >
107 Reference< XComponentContext > m_xContext;
109 public:
110 explicit TestBridgeImpl( const Reference< XComponentContext > & xContext )
111 : m_xContext( xContext )
114 // XServiceInfo
115 virtual OUString SAL_CALL getImplementationName() override;
116 virtual sal_Bool SAL_CALL supportsService( const OUString & rServiceName ) override;
117 virtual Sequence< OUString > SAL_CALL getSupportedServiceNames() override;
119 // XMain
120 virtual sal_Int32 SAL_CALL run( const Sequence< OUString > & rArgs ) override;
124 static bool equals( const TestElement & rData1, const TestElement & rData2 )
126 check( rData1.Bool == rData2.Bool, "### bool does not match!" );
127 check( rData1.Char == rData2.Char, "### char does not match!" );
128 check( rData1.Byte == rData2.Byte, "### byte does not match!" );
129 check( rData1.Short == rData2.Short, "### short does not match!" );
130 check( rData1.UShort == rData2.UShort, "### unsigned short does not match!" );
131 check( rData1.Long == rData2.Long, "### long does not match!" );
132 check( rData1.ULong == rData2.ULong, "### unsigned long does not match!" );
133 check( rData1.Hyper == rData2.Hyper, "### hyper does not match!" );
134 check( rData1.UHyper == rData2.UHyper, "### unsigned hyper does not match!" );
135 check( rData1.Float == rData2.Float, "### float does not match!" );
136 check( rData1.Double == rData2.Double, "### double does not match!" );
137 check( rData1.Enum == rData2.Enum, "### enum does not match!" );
138 check( rData1.String == rData2.String, "### string does not match!" );
139 check( rData1.Interface == rData2.Interface, "### interface does not match!" );
140 check( rData1.Any == rData2.Any, "### any does not match!" );
142 return (rData1.Bool == rData2.Bool &&
143 rData1.Char == rData2.Char &&
144 rData1.Byte == rData2.Byte &&
145 rData1.Short == rData2.Short &&
146 rData1.UShort == rData2.UShort &&
147 rData1.Long == rData2.Long &&
148 rData1.ULong == rData2.ULong &&
149 rData1.Hyper == rData2.Hyper &&
150 rData1.UHyper == rData2.UHyper &&
151 rData1.Float == rData2.Float &&
152 rData1.Double == rData2.Double &&
153 rData1.Enum == rData2.Enum &&
154 rData1.String == rData2.String &&
155 rData1.Interface == rData2.Interface &&
156 rData1.Any == rData2.Any);
159 static bool equals( const TestData & rData1, const TestData & rData2 )
161 sal_Int32 nLen;
163 if ((rData1.Sequence == rData2.Sequence) &&
164 equals( static_cast<const TestElement &>(rData1), static_cast<const TestElement &>(rData2) ) &&
165 (nLen = rData1.Sequence.getLength()) == rData2.Sequence.getLength())
167 // once again by hand sequence ==
168 const TestElement * pElements1 = rData1.Sequence.getConstArray();
169 const TestElement * pElements2 = rData2.Sequence.getConstArray();
170 for ( ; nLen--; )
172 if (! equals( pElements1[nLen], pElements2[nLen] ))
174 check( false, "### sequence element did not match!" );
175 return false;
178 return true;
180 return false;
183 static void assign( TestElement & rData,
184 bool bBool, sal_Unicode cChar, sal_Int8 nByte,
185 sal_Int16 nShort, sal_uInt16 nUShort,
186 sal_Int32 nLong, sal_uInt32 nULong,
187 sal_Int64 nHyper, sal_uInt64 nUHyper,
188 float fFloat, double fDouble,
189 TestEnum eEnum, const OUString& rStr,
190 const css::uno::Reference< css::uno::XInterface >& xTest,
191 const css::uno::Any& rAny )
193 rData.Bool = bBool;
194 rData.Char = cChar;
195 rData.Byte = nByte;
196 rData.Short = nShort;
197 rData.UShort = nUShort;
198 rData.Long = nLong;
199 rData.ULong = nULong;
200 rData.Hyper = nHyper;
201 rData.UHyper = nUHyper;
202 rData.Float = fFloat;
203 rData.Double = fDouble;
204 rData.Enum = eEnum;
205 rData.String = rStr;
206 rData.Interface = xTest;
207 rData.Any = rAny;
210 namespace {
212 template < typename T >
213 bool testAny(
214 T const & value, Reference< XBridgeTest > const & xLBT,
215 char const * typeName = nullptr)
217 Any any;
218 any <<= value;
219 Any any2 = xLBT->transportAny(any);
220 bool success = true;
221 if (any != any2) {
222 fprintf(
223 stderr, "any is different after roundtrip: in %s, out %s\n",
224 OUStringToOString(
225 any.getValueType().getTypeName(),
226 RTL_TEXTENCODING_ASCII_US).getStr(),
227 OUStringToOString(
228 any2.getValueType().getTypeName(),
229 RTL_TEXTENCODING_ASCII_US).getStr());
230 success = false;
232 if (typeName != nullptr
233 && !any2.getValueType().getTypeName().equalsAscii(typeName))
235 fprintf(
236 stderr, "any has wrong type after roundtrip: %s instead of %s\n",
237 OUStringToOString(
238 any2.getValueType().getTypeName(),
239 RTL_TEXTENCODING_ASCII_US).getStr(),
240 typeName);
241 success = false;
243 return success;
248 static bool performAnyTest( const Reference< XBridgeTest > &xLBT, const TestData &data)
250 bool bReturn = true;
251 bReturn = testAny( data.Byte ,xLBT ) && bReturn;
252 bReturn = testAny( data.Short,xLBT ) && bReturn;
253 bReturn = testAny( data.UShort,xLBT ) && bReturn;
254 bReturn = testAny( data.Long,xLBT ) && bReturn;
255 bReturn = testAny( data.ULong,xLBT ) && bReturn;
256 bReturn = testAny( data.Hyper,xLBT ) && bReturn;
257 bReturn = testAny( data.UHyper,xLBT ) && bReturn;
258 bReturn = testAny( data.Float,xLBT ) && bReturn;
259 bReturn = testAny( data.Double,xLBT ) && bReturn;
260 bReturn = testAny( data.Enum,xLBT ) && bReturn;
261 bReturn = testAny( data.String,xLBT ) && bReturn;
262 bReturn = testAny( data.Interface,xLBT ) && bReturn;
263 bReturn = testAny( data, xLBT ) && bReturn;
264 bReturn &= testAny(
265 TestPolyStruct< sal_Unicode >(' '), xLBT,
266 "test.testtools.bridgetest.TestPolyStruct<char>");
268 Any a;
270 a <<= data.Bool;
271 OSL_ASSERT( xLBT->transportAny( a ) == a );
275 a <<= data.Char;
276 OSL_ASSERT( xLBT->transportAny( a ) == a );
279 return bReturn;
283 static bool performSequenceOfCallTest( const Reference < XBridgeTest > &xLBT )
285 sal_Int32 i,nRounds;
286 sal_Int32 nGlobalIndex = 0;
287 const sal_Int32 nWaitTimeSpanMUSec = 10000;
288 for( nRounds = 0 ; nRounds < 10 ; nRounds ++ )
290 for( i = 0 ; i < nRounds ; i ++ )
292 // fire oneways
293 xLBT->callOneway( nGlobalIndex , nWaitTimeSpanMUSec );
294 nGlobalIndex ++;
297 // call synchron
298 xLBT->call( nGlobalIndex , nWaitTimeSpanMUSec );
299 nGlobalIndex ++;
302 return xLBT->sequenceOfCallTestPassed();
305 class ORecursiveCall : public WeakImplHelper< XRecursiveCall >
307 private:
308 Mutex m_mutex;
310 public:
311 void SAL_CALL callRecursivly(
312 const css::uno::Reference< XRecursiveCall >& xCall,
313 sal_Int32 nToCall ) override
315 MutexGuard guard( m_mutex );
316 if( nToCall )
318 nToCall --;
319 xCall->callRecursivly( this , nToCall );
326 static bool performRecursiveCallTest( const Reference < XBridgeTest > & xLBT )
328 xLBT->startRecursiveCall( new ORecursiveCall , 50 );
329 // on failure, the test would lock up or crash
330 return true;
333 class MyClass : public osl::DebugBase<MyClass>, public OWeakObject
335 public:
336 MyClass();
340 MyClass::MyClass()
344 static bool performTest(
345 const Reference<XComponentContext> & xContext,
346 const Reference<XBridgeTest > & xLBT,
347 bool noCurrentContext )
349 check(xLBT.is(), "### no test interface!");
350 bool bRet = true;
351 if (xLBT.is()) {
352 // this data is never ever granted access to by calls other than
353 // equals(), assign()!
354 TestData aData; // test against this data
355 Reference< XInterface > xI(new MyClass);
356 assign(
357 static_cast<TestElement &>(aData), true, '@', 17, 0x1234, 0xFEDC,
358 0x12345678, 0xFEDCBA98, SAL_CONST_INT64(0x123456789ABCDEF0),
359 SAL_CONST_UINT64(0xFEDCBA9876543210), 17.0815f, 3.1415926359,
360 TestEnum_LOLA, STRING_TEST_CONSTANT, xI,
361 Any(&xI, cppu::UnoType<XInterface>::get()));
362 bRet &= check(aData.Any == xI, "### unexpected any!");
363 bRet &= check(!(aData.Any != xI), "### unexpected any!");
364 aData.Sequence.realloc(2);
365 aData.Sequence[0] = *static_cast<TestElement const *>(&aData);
366 // aData.Sequence[1] is empty
367 // aSetData is a manually copy of aData for first setting:
368 TestData aSetData;
369 assign(
370 static_cast<TestElement &>(aSetData), aData.Bool, aData.Char,
371 aData.Byte, aData.Short, aData.UShort, aData.Long, aData.ULong,
372 aData.Hyper, aData.UHyper, aData.Float, aData.Double, aData.Enum,
373 aData.String, xI, Any(&xI, cppu::UnoType<XInterface>::get()));
374 aSetData.Sequence.realloc(2);
375 aSetData.Sequence[0] = *static_cast<TestElement const *>(&aSetData);
376 // aSetData.Sequence[1] is empty
377 xLBT->setValues(
378 aSetData.Bool, aSetData.Char, aSetData.Byte, aSetData.Short,
379 aSetData.UShort, aSetData.Long, aSetData.ULong, aSetData.Hyper,
380 aSetData.UHyper, aSetData.Float, aSetData.Double, aSetData.Enum,
381 aSetData.String, aSetData.Interface, aSetData.Any,
382 aSetData.Sequence, aSetData);
384 TestData aRet;
385 TestData aRet2;
386 xLBT->getValues(
387 aRet.Bool, aRet.Char, aRet.Byte, aRet.Short, aRet.UShort,
388 aRet.Long, aRet.ULong, aRet.Hyper, aRet.UHyper, aRet.Float,
389 aRet.Double, aRet.Enum, aRet.String, aRet.Interface, aRet.Any,
390 aRet.Sequence, aRet2);
391 bRet &= check(
392 equals(aData, aRet) && equals(aData, aRet2), "getValues test");
393 // Set last retrieved values:
394 TestData aSV2ret(
395 xLBT->setValues2(
396 aRet.Bool, aRet.Char, aRet.Byte, aRet.Short, aRet.UShort,
397 aRet.Long, aRet.ULong, aRet.Hyper, aRet.UHyper, aRet.Float,
398 aRet.Double, aRet.Enum, aRet.String, aRet.Interface,
399 aRet.Any, aRet.Sequence, aRet2));
400 // Check inout sequence order (=> inout sequence parameter was
401 // switched by test objects):
402 TestElement temp(aRet.Sequence[0]);
403 aRet.Sequence[0] = aRet.Sequence[1];
404 aRet.Sequence[1] = temp;
405 bRet &= check(
406 equals(aData, aSV2ret) && equals(aData, aRet2),
407 "getValues2 test");
410 TwoFloats aIn(1.1f, 2.2f);
411 TwoFloats aOut = xLBT->echoTwoFloats(aIn);
412 bRet = check( memcmp(&aIn, &aOut, sizeof(TwoFloats)) == 0, "two floats struct test" ) && bRet;
415 FourFloats aIn(3.3f, 4.4f, 5.5f, 6.6f);
416 FourFloats aOut = xLBT->echoFourFloats(aIn);
417 bRet = check( memcmp(&aIn, &aOut, sizeof(FourFloats)) == 0, "four floats struct test" ) && bRet;
420 MixedFloatAndInteger aIn(7.7f, 8);
421 MixedFloatAndInteger aOut = xLBT->echoMixedFloatAndInteger(aIn);
422 bRet = check( memcmp(&aIn, &aOut, sizeof(MixedFloatAndInteger)) == 0, "mixed float and integer struct test" ) && bRet;
425 ThreeByteStruct aIn(9, 10, 11);
426 ThreeByteStruct aOut = xLBT->echoThreeByteStruct(aIn);
427 bRet = check( memcmp(&aIn, &aOut, sizeof(ThreeByteStruct)) == 0, "three byte struct test" ) && bRet;
430 TestData aRet;
431 TestData aRet2;
432 TestData aGVret(
433 xLBT->getValues(
434 aRet.Bool, aRet.Char, aRet.Byte, aRet.Short, aRet.UShort,
435 aRet.Long, aRet.ULong, aRet.Hyper, aRet.UHyper, aRet.Float,
436 aRet.Double, aRet.Enum, aRet.String, aRet.Interface,
437 aRet.Any, aRet.Sequence, aRet2));
438 bRet &= check(
439 (equals(aData, aRet) && equals(aData, aRet2) &&
440 equals(aData, aGVret)),
441 "getValues test");
442 // Set last retrieved values:
443 xLBT->setBool(aRet.Bool);
444 xLBT->setChar(aRet.Char);
445 xLBT->setByte(aRet.Byte);
446 xLBT->setShort(aRet.Short);
447 xLBT->setUShort(aRet.UShort);
448 xLBT->setLong(aRet.Long);
449 xLBT->setULong(aRet.ULong);
450 xLBT->setHyper(aRet.Hyper);
451 xLBT->setUHyper(aRet.UHyper);
452 xLBT->setFloat(aRet.Float);
453 xLBT->setDouble(aRet.Double);
454 xLBT->setEnum(aRet.Enum);
455 xLBT->setString(aRet.String);
456 xLBT->setInterface(aRet.Interface);
457 xLBT->setAny(aRet.Any);
458 xLBT->setSequence(aRet.Sequence);
459 xLBT->setStruct(aRet2);
462 TestData aRet;
463 aRet.Hyper = xLBT->getHyper();
464 aRet.UHyper = xLBT->getUHyper();
465 aRet.Float = xLBT->getFloat();
466 aRet.Double = xLBT->getDouble();
467 aRet.Byte = xLBT->getByte();
468 aRet.Char = xLBT->getChar();
469 aRet.Bool = xLBT->getBool();
470 aRet.Short = xLBT->getShort();
471 aRet.UShort = xLBT->getUShort();
472 aRet.Long = xLBT->getLong();
473 aRet.ULong = xLBT->getULong();
474 aRet.Enum = xLBT->getEnum();
475 aRet.String = xLBT->getString();
476 aRet.Interface = xLBT->getInterface();
477 aRet.Any = xLBT->getAny();
478 aRet.Sequence = xLBT->getSequence();
479 TestData aRet2(xLBT->getStruct());
480 bRet &= check(
481 equals(aData, aRet) && equals(aData, aRet2),
482 "struct comparison test");
484 SmallStruct aIn(1, 2);
485 SmallStruct aOut(xLBT->echoSmallStruct(aIn));
486 bRet &= check(
487 memcmp(&aIn, &aOut, sizeof(SmallStruct)) == 0,
488 "small struct test");
491 MediumStruct aIn(1, 2, 3, 4);
492 MediumStruct aOut(xLBT->echoMediumStruct(aIn));
493 bRet &= check(
494 memcmp(&aIn, &aOut, sizeof(MediumStruct)) == 0,
495 "medium struct test");
498 BigStruct aIn(1, 2, 3, 4, 5, 6, 7, 8);
499 BigStruct aOut(xLBT->echoBigStruct(aIn));
500 bRet &= check(
501 memcmp(&aIn, &aOut, sizeof(BigStruct)) == 0,
502 "big struct test");
505 sal_Int32 i2 = xLBT->testPPCAlignment(0, 0, 0, 0, 0xBEAF);
506 bRet &= check(i2 == 0xBEAF, "ppc-style alignment test");
509 sal_Int32 i1 = xLBT->testPPC64Alignment(1.0, 2.0, 3.0, 0xBEAF);
510 bRet &= check(i1 == 0xBEAF, "ppc64-style alignment test");
513 double d1 = xLBT->testTenDoubles(0.1, 0.2, 0.3, 0.4, 0.5,
514 0.6, 0.7, 0.8, 0.9, 1.0);
515 bRet &= check(d1 == 5.5, "armhf doubles test");
517 // Test extended attributes that raise exceptions:
518 try {
519 xLBT->getRaiseAttr1();
520 bRet &= check(false, "getRaiseAttr1 did not throw");
521 } catch (const RuntimeException &) {
522 } catch (...) {
523 bRet &= check(false, "getRaiseAttr1 threw wrong type");
525 try {
526 xLBT->setRaiseAttr1(0);
527 bRet &= check(false, "setRaiseAttr1 did not throw");
528 } catch (const IllegalArgumentException &) {
529 } catch (...) {
530 bRet &= check(false, "setRaiseAttr1 threw wrong type");
532 try {
533 xLBT->getRaiseAttr2();
534 bRet &= check(false, "getRaiseAttr2 did not throw");
535 } catch (const IllegalArgumentException &) {
536 } catch (...) {
537 bRet &= check(false, "getRaiseAttr2 threw wrong type");
539 // Test instantiated polymorphic struct types:
541 bRet &= check(
542 (xLBT->transportPolyBoolean(
543 TestPolyStruct< sal_Bool >(true)).
544 member),
545 "transportPolyBoolean");
546 TestPolyStruct< sal_Int64 > tps1(12345);
547 xLBT->transportPolyHyper(tps1);
548 bRet &= check(tps1.member == 12345, "transportPolyHyper");
549 Sequence< Any > seq(2);
550 seq[0] <<= static_cast< sal_uInt32 >(33);
551 seq[1] <<= OUString("ABC");
552 TestPolyStruct< Sequence< Any > > tps2(seq);
553 TestPolyStruct< Sequence< Any > > tps3;
554 xLBT->transportPolySequence(tps2, tps3);
555 bRet &= check(
556 tps3.member.getLength() == 2,
557 "transportPolySequence, length");
558 sal_uInt32 v0 = sal_uInt32();
559 tps3.member[0] >>= v0;
560 bRet &= check(v0 == 33, "transportPolySequence, element 0");
561 OUString v1;
562 tps3.member[1] >>= v1;
563 bRet &= check( v1 == "ABC", "transportPolySequence, element 1" );
564 bRet &= check(
565 xLBT->getNullPolyLong().member == 0, "getNullPolyLong");
566 bRet &= check(
567 xLBT->getNullPolyString().member.isEmpty(),
568 "getNullPolyString");
569 bRet &= check(
570 xLBT->getNullPolyType().member == Type(),
571 "getNullPolyType");
572 Any nullAny(xLBT->getNullPolyAny().member);
573 auto ifc = o3tl::tryAccess<Reference<XInterface>>(nullAny);
574 bRet &= check(
575 !nullAny.hasValue() || (ifc && !ifc->is()),
576 "getNullPolyAny");
577 bRet &= check(
578 !xLBT->getNullPolySequence().member.hasElements(),
579 "getNullPolySequence");
580 bRet &= check(
581 xLBT->getNullPolyEnum().member == TestEnum_TEST,
582 "getNullPolyEnum");
583 bRet &= check(
584 xLBT->getNullPolyBadEnum().member == TestBadEnum_M,
585 "getNullPolyBadEnum");
586 bRet &= check(
587 xLBT->getNullPolyStruct().member.member == 0,
588 "getNullPolyStruct");
589 bRet &= check(
590 !xLBT->getNullPolyInterface().member.is(),
591 "getNullPolyInterface");
593 // Any test:
594 bRet &= check(performAnyTest(xLBT , aData), "any test");
595 // Sequence of call test:
596 bRet &= check(
597 performSequenceOfCallTest(xLBT), "sequence of call test");
598 // Recursive call test:
599 bRet &= check(performRecursiveCallTest(xLBT), "recursive test");
600 bRet &= check(
601 equals(aData, aRet) && equals(aData, aRet2),
602 "recursive test results");
603 // Multiple inheritance test:
604 bRet &= checkEmpty(
605 testtools::bridgetest::testMulti(xLBT->getMulti()),
606 "remote multi");
607 bRet &= checkEmpty(
608 xLBT->testMulti(new testtools::bridgetest::Multi),
609 "local multi");
613 Reference< XBridgeTest2 > xBT2(xLBT, UNO_QUERY);
614 if (!xBT2.is()) {
615 return bRet;
617 // Perform sequence tests (XBridgeTest2); create the sequence which is
618 // compared with the results:
619 sal_Int32 _arLong[] = {
620 static_cast< sal_Int32 >(0x80000000), 1, 0x7FFFFFFF };
621 sal_Int32 _aInt = 0xBABEBABE;
622 float _aFloat = 3.14f;
623 Any _any1(true);
624 Any _any2(&_aInt, cppu::UnoType<sal_Int32>::get());
625 Any _any3(&_aFloat, cppu::UnoType<float>::get());
626 Any _arAny[] = { _any1, _any2, _any3 };
627 Reference< XInterface > _arObj[3];
628 _arObj[0] = new OWeakObject();
629 _arObj[1] = new OWeakObject();
630 _arObj[2] = new OWeakObject();
631 TestElement _arStruct[3];
632 assign(
633 _arStruct[0], true, '@', 17, 0x1234, 0xFEDC, 0x12345678, 0xFEDCBA98,
634 SAL_CONST_INT64(0x123456789ABCDEF0),
635 SAL_CONST_UINT64(0xFEDCBA9876543210), 17.0815f, 3.1415926359,
636 TestEnum_LOLA, STRING_TEST_CONSTANT, _arObj[0],
637 Any(&_arObj[0], cppu::UnoType<XInterface>::get()));
638 assign(
639 _arStruct[1], true, 'A', 17, 0x1234, 0xFEDC, 0x12345678, 0xFEDCBA98,
640 SAL_CONST_INT64(0x123456789ABCDEF0),
641 SAL_CONST_UINT64(0xFEDCBA9876543210), 17.0815f, 3.1415926359,
642 TestEnum_TWO, STRING_TEST_CONSTANT, _arObj[1],
643 Any(&_arObj[1], cppu::UnoType<XInterface>::get()));
644 assign(
645 _arStruct[2], true, 'B', 17, 0x1234, 0xFEDC, 0x12345678, 0xFEDCBA98,
646 SAL_CONST_INT64(0x123456789ABCDEF0),
647 SAL_CONST_UINT64(0xFEDCBA9876543210), 17.0815f, 3.1415926359,
648 TestEnum_CHECK, STRING_TEST_CONSTANT, _arObj[2],
649 Any(&_arObj[2], cppu::UnoType<XInterface>::get()));
651 Sequence<sal_Bool> arBool({true, false, true});
652 Sequence<sal_Unicode> arChar({0x0065, 0x0066, 0x0067});
653 Sequence<sal_Int8> arByte({1, 2, -1});
654 Sequence<sal_Int16> arShort({-0x8000, 1, 0x7FFF});
655 Sequence<sal_uInt16> arUShort({0 , 1, 0xFFFF});
656 Sequence<sal_Int32> arLong(_arLong, 3);
657 Sequence<sal_uInt32> arULong({0, 1, 0xFFFFFFFF});
658 Sequence<sal_Int64> arHyper({
659 static_cast<sal_Int64>(SAL_CONST_INT64(0x8000000000000000)), 1,
660 SAL_CONST_INT64(0x7FFFFFFFFFFFFFFF)});
661 Sequence<sal_uInt64> arUHyper({
662 0, 1, SAL_CONST_UINT64(0xFFFFFFFFFFFFFFFF)});
663 Sequence<float> arFloat({1.1f, 2.2f, 3.3f});
664 Sequence<double> arDouble({1.11, 2.22, 3.33});
665 Sequence<OUString> arString({
666 OUString("String 1"), OUString("String 2"),
667 OUString("String 3")});
668 Sequence<Any> arAny(_arAny, 3);
669 Sequence<Reference<XInterface> > arObject(_arObj, 3);
670 Sequence<TestEnum> arEnum({
671 TestEnum_ONE, TestEnum_TWO, TestEnum_CHECK});
672 Sequence<TestElement> arStruct(_arStruct, 3);
673 Sequence<Sequence<sal_Int32> > _arSeqLong2[3];
674 for (int j = 0; j != 3; ++j) {
675 Sequence< sal_Int32 > _arSeqLong[3];
676 for (int i = 0; i != 3; ++i) {
677 _arSeqLong[i] = Sequence< sal_Int32 >(_arLong, 3);
679 _arSeqLong2[j] = Sequence< Sequence< sal_Int32 > >(
680 _arSeqLong, 3);
682 Sequence< Sequence< Sequence< sal_Int32> > > arLong3(
683 _arSeqLong2, 3);
684 Sequence< Sequence< sal_Int32 > > seqSeqRet(
685 xBT2->setDim2(arLong3[0]));
686 bRet &= check(seqSeqRet == arLong3[0], "sequence test");
687 Sequence< Sequence< Sequence< sal_Int32 > > > seqSeqRet2(
688 xBT2->setDim3(arLong3));
689 bRet &= check(seqSeqRet2 == arLong3, "sequence test");
690 Sequence< Any > seqAnyRet(xBT2->setSequenceAny(arAny));
691 bRet &= check(seqAnyRet == arAny, "sequence test");
692 Sequence< sal_Bool > seqBoolRet(xBT2->setSequenceBool(arBool));
693 bRet &= check(seqBoolRet == arBool, "sequence test");
694 Sequence< sal_Int8 > seqByteRet(xBT2->setSequenceByte(arByte));
695 bRet &= check(seqByteRet == arByte, "sequence test");
696 Sequence< sal_Unicode > seqCharRet(xBT2->setSequenceChar(arChar));
697 bRet &= check(seqCharRet == arChar, "sequence test");
698 Sequence< sal_Int16 > seqShortRet(xBT2->setSequenceShort(arShort));
699 bRet &= check(seqShortRet == arShort, "sequence test");
700 Sequence< sal_Int32 > seqLongRet(xBT2->setSequenceLong(arLong));
701 bRet &= check(seqLongRet == arLong, "sequence test");
702 Sequence< sal_Int64 > seqHyperRet(xBT2->setSequenceHyper(arHyper));
703 bRet &= check(seqHyperRet == arHyper, "sequence test");
704 Sequence< float > seqFloatRet(xBT2->setSequenceFloat(arFloat));
705 bRet &= check(seqFloatRet == arFloat, "sequence test");
706 Sequence< double > seqDoubleRet(xBT2->setSequenceDouble(arDouble));
707 bRet &= check(seqDoubleRet == arDouble, "sequence test");
708 Sequence< TestEnum > seqEnumRet(xBT2->setSequenceEnum(arEnum));
709 bRet &= check(seqEnumRet == arEnum, "sequence test");
710 Sequence< sal_uInt16 > seqUShortRet(
711 xBT2->setSequenceUShort(arUShort));
712 bRet &= check(seqUShortRet == arUShort, "sequence test");
713 Sequence< sal_uInt32 > seqULongRet(xBT2->setSequenceULong(arULong));
714 bRet &= check(seqULongRet == arULong, "sequence test");
715 Sequence< sal_uInt64 > seqUHyperRet(
716 xBT2->setSequenceUHyper(arUHyper));
717 bRet &= check(seqUHyperRet == arUHyper, "sequence test");
718 Sequence< Reference< XInterface > > seqObjectRet(
719 xBT2->setSequenceXInterface(arObject));
720 bRet &= check(seqObjectRet == arObject, "sequence test");
721 Sequence< OUString > seqStringRet(
722 xBT2->setSequenceString(arString));
723 bRet &= check(seqStringRet == arString, "sequence test");
724 Sequence< TestElement > seqStructRet(
725 xBT2->setSequenceStruct(arStruct));
726 bRet &= check(seqStructRet == arStruct, "sequence test");
727 Sequence< sal_Bool > arBoolTemp(cloneSequence(arBool));
728 Sequence< sal_Unicode > arCharTemp(cloneSequence<sal_Unicode, cppu::UnoCharType>(arChar));
729 Sequence< sal_Int8 > arByteTemp(cloneSequence(arByte));
730 Sequence< sal_Int16 > arShortTemp(cloneSequence(arShort));
731 Sequence< sal_uInt16 > arUShortTemp(cloneSequence<sal_uInt16, cppu::UnoUnsignedShortType>(arUShort));
732 Sequence< sal_Int32 > arLongTemp(cloneSequence(arLong));
733 Sequence< sal_uInt32 > arULongTemp(cloneSequence(arULong));
734 Sequence< sal_Int64 > arHyperTemp(cloneSequence(arHyper));
735 Sequence< sal_uInt64 > arUHyperTemp(cloneSequence(arUHyper));
736 Sequence< float > arFloatTemp(cloneSequence(arFloat));
737 Sequence< double > arDoubleTemp(cloneSequence(arDouble));
738 Sequence< TestEnum > arEnumTemp(cloneSequence(arEnum));
739 Sequence< OUString > arStringTemp(cloneSequence(arString));
740 Sequence< Reference< XInterface > > arObjectTemp(
741 cloneSequence(arObject));
742 Sequence< Any > arAnyTemp(cloneSequence(arAny));
743 Sequence< Sequence< sal_Int32 > > arLong2Temp(arLong3[0]);
744 Sequence< Sequence< Sequence< sal_Int32 > > > arLong3Temp(arLong3);
745 xBT2->setSequencesInOut(
746 arBoolTemp, arCharTemp, arByteTemp, arShortTemp, arUShortTemp,
747 arLongTemp,arULongTemp, arHyperTemp, arUHyperTemp, arFloatTemp,
748 arDoubleTemp, arEnumTemp, arStringTemp, arObjectTemp, arAnyTemp,
749 arLong2Temp, arLong3Temp);
750 bRet &= check(
751 (arBoolTemp == arBool && arCharTemp == arChar &&
752 arByteTemp == arByte && arShortTemp == arShort &&
753 arUShortTemp == arUShort && arLongTemp == arLong &&
754 arULongTemp == arULong && arHyperTemp == arHyper &&
755 arUHyperTemp == arUHyper && arFloatTemp == arFloat &&
756 arDoubleTemp == arDouble && arEnumTemp == arEnum &&
757 arStringTemp == arString && arObjectTemp == arObject &&
758 arAnyTemp == arAny && arLong2Temp == arLong3[0] &&
759 arLong3Temp == arLong3),
760 "sequence test");
761 Sequence< sal_Bool > arBoolOut;
762 Sequence< sal_Unicode > arCharOut;
763 Sequence< sal_Int8 > arByteOut;
764 Sequence< sal_Int16 > arShortOut;
765 Sequence< sal_uInt16 > arUShortOut;
766 Sequence< sal_Int32 > arLongOut;
767 Sequence< sal_uInt32 > arULongOut;
768 Sequence< sal_Int64 > arHyperOut;
769 Sequence< sal_uInt64 > arUHyperOut;
770 Sequence< float > arFloatOut;
771 Sequence< double > arDoubleOut;
772 Sequence< TestEnum > arEnumOut;
773 Sequence< OUString > arStringOut;
774 Sequence< Reference< XInterface > > arObjectOut;
775 Sequence< Any > arAnyOut;
776 Sequence< Sequence< sal_Int32 > > arLong2Out;
777 Sequence< Sequence< Sequence< sal_Int32 > > > arLong3Out;
778 xBT2->setSequencesOut(
779 arBoolOut, arCharOut, arByteOut, arShortOut, arUShortOut,
780 arLongOut,arULongOut, arHyperOut, arUHyperOut, arFloatOut,
781 arDoubleOut, arEnumOut, arStringOut, arObjectOut, arAnyOut,
782 arLong2Out, arLong3Out);
783 bRet &= check(
784 (arBoolOut == arBool && arCharOut == arChar &&
785 arByteOut == arByte && arShortOut == arShort &&
786 arUShortOut == arUShort && arLongOut == arLong &&
787 arULongOut == arULong && arHyperOut == arHyper &&
788 arUHyperOut == arUHyper && arFloatOut == arFloat &&
789 arDoubleOut == arDouble && arEnumOut == arEnum &&
790 arStringOut == arString && arObjectOut == arObject &&
791 arAnyOut == arAny && arLong2Out == arLong3[0] &&
792 arLong3Out == arLong3),
793 "sequence test");
796 // Test with empty sequences:
797 Sequence< Sequence< sal_Int32 > > arLong2;
798 Sequence< Sequence< sal_Int32 > > seqSeqRet(xBT2->setDim2(arLong2));
799 bRet &= check(seqSeqRet == arLong2, "sequence test");
800 Sequence< Sequence< Sequence< sal_Int32 > > > arLong3;
801 Sequence< Sequence< Sequence< sal_Int32 > > > seqSeqRet2(
802 xBT2->setDim3(arLong3));
803 bRet &= check(seqSeqRet2 == arLong3, "sequence test");
804 Sequence< Any > arAny;
805 Sequence< Any > seqAnyRet(xBT2->setSequenceAny(arAny));
806 bRet &= check(seqAnyRet == arAny, "sequence test");
807 Sequence< sal_Bool > arBool;
808 Sequence< sal_Bool > seqBoolRet(xBT2->setSequenceBool(arBool));
809 bRet &= check(seqBoolRet == arBool, "sequence test");
810 Sequence< sal_Int8 > arByte;
811 Sequence< sal_Int8 > seqByteRet(xBT2->setSequenceByte(arByte));
812 bRet &= check(seqByteRet == arByte, "sequence test");
813 Sequence< sal_Unicode > arChar;
814 Sequence< sal_Unicode > seqCharRet(xBT2->setSequenceChar(arChar));
815 bRet &= check(seqCharRet == arChar, "sequence test");
816 Sequence< sal_Int16 > arShort;
817 Sequence< sal_Int16 > seqShortRet(xBT2->setSequenceShort(arShort));
818 bRet &= check(seqShortRet == arShort, "sequence test");
819 Sequence< sal_Int32 > arLong;
820 Sequence< sal_Int32 > seqLongRet(xBT2->setSequenceLong(arLong));
821 bRet &= check(seqLongRet == arLong, "sequence test");
822 Sequence< sal_Int64 > arHyper;
823 Sequence< sal_Int64 > seqHyperRet(xBT2->setSequenceHyper(arHyper));
824 bRet &= check(seqHyperRet == arHyper, "sequence test");
825 Sequence< float > arFloat;
826 Sequence< float > seqFloatRet(xBT2->setSequenceFloat(arFloat));
827 bRet &= check(seqFloatRet == arFloat, "sequence test");
828 Sequence< double > arDouble;
829 Sequence< double > seqDoubleRet(xBT2->setSequenceDouble(arDouble));
830 bRet &= check(seqDoubleRet == arDouble, "sequence test");
831 Sequence< TestEnum > arEnum;
832 Sequence< TestEnum > seqEnumRet(xBT2->setSequenceEnum(arEnum));
833 bRet &= check(seqEnumRet == arEnum, "sequence test");
834 Sequence< sal_uInt16 > arUShort;
835 Sequence< sal_uInt16 > seqUShortRet(
836 xBT2->setSequenceUShort(arUShort));
837 bRet &= check(seqUShortRet == arUShort, "sequence test");
838 Sequence< sal_uInt32 > arULong;
839 Sequence< sal_uInt32 > seqULongRet(xBT2->setSequenceULong(arULong));
840 bRet &= check(seqULongRet == arULong, "sequence test");
841 Sequence< sal_uInt64 > arUHyper;
842 Sequence< sal_uInt64 > seqUHyperRet(
843 xBT2->setSequenceUHyper(arUHyper));
844 bRet &= check(seqUHyperRet == arUHyper, "sequence test");
845 Sequence< Reference< XInterface > > arObject;
846 Sequence< Reference< XInterface > > seqObjectRet(
847 xBT2->setSequenceXInterface(arObject));
848 bRet &= check(seqObjectRet == arObject, "sequence test");
849 Sequence< OUString > arString;
850 Sequence< OUString > seqStringRet(
851 xBT2->setSequenceString(arString));
852 bRet &= check(seqStringRet == arString, "sequence test");
853 Sequence< TestElement > arStruct;
854 Sequence< TestElement > seqStructRet(
855 xBT2->setSequenceStruct(arStruct));
856 bRet &= check(seqStructRet == arStruct, "sequence test");
858 // Issue #i60341# shows that the most interesting case is were Java
859 // calls the constructors; however, since this client is currently not
860 // available in Java, while the server is, the logic is reversed here:
861 try {
862 xBT2->testConstructorsService(xContext);
863 } catch (const BadConstructorArguments &) {
864 bRet = false;
866 if (!noCurrentContext) {
867 if (!(new testtools::bridgetest::CurrentContextChecker)->perform(
868 xBT2->getCurrentContextChecker(), 0, 1))
870 bRet = false;
872 if (!(new testtools::bridgetest::CurrentContextChecker)->perform(
873 xBT2->getCurrentContextChecker(), 0, 2))
875 bRet = false;
877 if (!(new testtools::bridgetest::CurrentContextChecker)->perform(
878 xBT2->getCurrentContextChecker(), 1, 2))
880 bRet = false;
882 if (!(new testtools::bridgetest::CurrentContextChecker)->perform(
883 xBT2->getCurrentContextChecker(), 1, 3))
885 bRet = false;
889 return bRet;
892 static bool raiseOnewayException( const Reference < XBridgeTest > & xLBT )
894 bool bReturn = true;
895 OUString sCompare = STRING_TEST_CONSTANT;
896 Reference<XInterface> const x(xLBT->getInterface());
899 // Note : the exception may fly or not (e.g. remote scenario).
900 // When it flies, it must contain the correct elements.
901 xLBT->raiseRuntimeExceptionOneway( sCompare, x );
903 catch( const RuntimeException & e )
905 bReturn = (
906 #if OSL_DEBUG_LEVEL == 0
907 // java stack traces trash Message
908 e.Message == sCompare &&
909 #endif
910 xLBT->getInterface() == e.Context &&
911 x == e.Context );
913 return bReturn;
917 static bool raiseException( const Reference< XBridgeTest > & xLBT )
919 sal_Int32 nCount = 0;
926 TestData aRet, aRet2;
927 xLBT->raiseException(
928 5, STRING_TEST_CONSTANT,
929 xLBT->getInterface() );
931 catch (const IllegalArgumentException &rExc)
933 if (rExc.ArgumentPosition == 5 &&
934 #if OSL_DEBUG_LEVEL == 0
935 // java stack traces trash Message
936 rExc.Message == STRING_TEST_CONSTANT &&
937 #endif
938 rExc.Context == xLBT->getInterface())
940 #ifdef COMPCHECK
941 //When we check if a new compiler still works then we must not call
942 //getRuntimeException because it uses cppu::getCaughtException which
943 //does only work if all libs are build with the same runtime.
944 return true;
945 #else
946 ++nCount;
947 #endif
949 else
951 check( false, "### unexpected exception content!" );
954 /** it is certain, that the RuntimeException testing will fail, if no */
955 xLBT->getRuntimeException();
958 catch (const RuntimeException & rExc)
960 if (rExc.Context == xLBT->getInterface()
961 #if OSL_DEBUG_LEVEL == 0
962 // java stack traces trash Message
963 && rExc.Message == STRING_TEST_CONSTANT
964 #endif
967 ++nCount;
969 else
971 check( false, "### unexpected exception content!" );
974 /** it is certain, that the RuntimeException testing will fail, if no */
975 xLBT->setRuntimeException( 0xcafebabe );
978 catch (const Exception & rExc)
980 if (rExc.Context == xLBT->getInterface()
981 #if OSL_DEBUG_LEVEL == 0
982 // java stack traces trash Message
983 && rExc.Message == STRING_TEST_CONSTANT
984 #endif
987 ++nCount;
989 else
991 check( false, "### unexpected exception content!" );
993 return (nCount == 3);
995 return false;
998 /* Returns an acquired sequence
1000 static uno_Sequence* cloneSequence(const uno_Sequence* val, const Type& type)
1002 TypeDescription td(type);
1003 td.makeComplete();
1004 typelib_TypeDescription* pTdRaw = td.get();
1005 typelib_IndirectTypeDescription* pIndirectTd =
1006 reinterpret_cast<typelib_IndirectTypeDescription*>(pTdRaw);
1008 typelib_TypeDescription* pTdElem = pIndirectTd->pType->pType;
1009 std::unique_ptr<sal_Int8[]> buf(new sal_Int8[pTdElem->nSize * val->nElements]);
1010 sal_Int8* pBufCur = buf.get();
1012 uno_Sequence* retSeq = nullptr;
1013 switch (static_cast<TypeClass>(pTdElem->eTypeClass))
1015 case TypeClass_SEQUENCE:
1017 Type _tElem(pTdElem->pWeakRef);
1018 for (int i = 0; i < val->nElements; i++)
1020 sal_Int8 const *pValBuf = reinterpret_cast<sal_Int8 const *>(&val->elements + i * pTdElem->nSize);
1022 uno_Sequence* seq = cloneSequence(
1023 reinterpret_cast<uno_Sequence const *>(pValBuf),
1024 _tElem);
1025 *reinterpret_cast<uno_Sequence**>(pBufCur) = seq;
1026 pBufCur += pTdElem->nSize;
1028 break;
1030 default:
1031 uno_type_sequence_construct(
1032 &retSeq, type.getTypeLibType(), const_cast<char *>(val->elements),
1033 val->nElements, reinterpret_cast< uno_AcquireFunc >(cpp_acquire));
1034 break;
1036 return retSeq;
1039 template<typename T, typename U>
1040 Sequence<T> cloneSequence(const Sequence<T>& val)
1042 Sequence<T> seq( cloneSequence(val.get(), cppu::UnoType<cppu::UnoSequenceType<U>>::get()), SAL_NO_ACQUIRE);
1043 return seq;
1046 template< class T >
1047 static bool makeSurrogate(
1048 Reference< T > & rOut, Reference< T > const & rOriginal )
1050 rOut.clear();
1051 if (! rOriginal.is())
1052 return false;
1054 Environment aCppEnv_official;
1055 Environment aUnoEnv_ano;
1056 Environment aCppEnv_ano;
1058 OUString aCppEnvTypeName(
1059 CPPU_CURRENT_LANGUAGE_BINDING_NAME );
1060 OUString aUnoEnvTypeName(
1061 UNO_LB_UNO );
1062 // official:
1063 uno_getEnvironment(
1064 reinterpret_cast< uno_Environment ** >( &aCppEnv_official ),
1065 aCppEnvTypeName.pData, nullptr );
1066 // anonymous:
1067 uno_createEnvironment(
1068 reinterpret_cast< uno_Environment ** >( &aCppEnv_ano ),
1069 aCppEnvTypeName.pData, nullptr );
1070 uno_createEnvironment(
1071 reinterpret_cast< uno_Environment ** >( &aUnoEnv_ano ),
1072 aUnoEnvTypeName.pData, nullptr );
1074 UnoInterfaceReference unoI;
1075 Mapping cpp2uno( aCppEnv_official.get(), aUnoEnv_ano.get() );
1076 Mapping uno2cpp( aUnoEnv_ano.get(), aCppEnv_ano.get() );
1077 if (!cpp2uno.is() || !uno2cpp.is())
1079 throw RuntimeException("cannot get C++-UNO mappings!" );
1081 cpp2uno.mapInterface(
1082 reinterpret_cast< void ** >( &unoI.m_pUnoI ),
1083 rOriginal.get(), cppu::UnoType<decltype(rOriginal)>::get() );
1084 if (! unoI.is())
1086 throw RuntimeException(
1087 "mapping C++ to binary UNO failed!" );
1089 uno2cpp.mapInterface(
1090 reinterpret_cast< void ** >( &rOut ),
1091 unoI.get(), cppu::UnoType<decltype(rOriginal)>::get() );
1092 if (! rOut.is())
1094 throw RuntimeException(
1095 "mapping binary UNO to C++ failed!" );
1098 return rOut.is();
1102 sal_Int32 TestBridgeImpl::run( const Sequence< OUString > & rArgs )
1104 bool bRet = false;
1107 if (! rArgs.hasElements())
1109 throw RuntimeException( "no test object specified!\n"
1110 "usage : ServiceName of test object | -u unourl of test object" );
1113 Reference< XInterface > xOriginal;
1114 bool remote;
1115 sal_Int32 i;
1116 if( rArgs.getLength() > 1 && rArgs[0] == "-u" )
1118 remote = true;
1119 i = 2;
1121 else
1123 remote = false;
1124 i = 1;
1126 bool noCurrentContext = false;
1127 if ( i < rArgs.getLength() && rArgs[i] == "noCurrentContext" )
1129 noCurrentContext = true;
1130 ++i;
1132 bool stress = false;
1133 if ( i < rArgs.getLength() && rArgs[i] == "stress" )
1135 stress = true;
1136 ++i;
1139 for (;;) {
1140 Reference< XInterface > o;
1141 if (remote) {
1142 o = UnoUrlResolver::create(m_xContext)->resolve(rArgs[1]);
1143 } else {
1144 o = m_xContext->getServiceManager()->createInstanceWithContext(
1145 rArgs[0], m_xContext);
1147 if (!stress) {
1148 xOriginal = o;
1149 break;
1153 if (! xOriginal.is())
1155 throw RuntimeException( "cannot get test object!" );
1157 Reference< XBridgeTest > xTest( xOriginal, UNO_QUERY_THROW );
1159 Reference<XBridgeTest > xLBT;
1160 bRet = check( makeSurrogate( xLBT, xTest ), "makeSurrogate" );
1161 bRet = check(
1162 performTest( m_xContext, xLBT, noCurrentContext ), "standard test" )
1163 && bRet;
1164 bRet = check( raiseException( xLBT ) , "exception test" )&& bRet;
1165 bRet = check( raiseOnewayException( xLBT ),
1166 "oneway exception test" ) && bRet;
1167 if (! bRet)
1169 throw RuntimeException( "error: test failed!" );
1172 catch (const Exception & exc)
1174 OString cstr( OUStringToOString( exc.Message, RTL_TEXTENCODING_ASCII_US ) );
1175 fprintf( stderr, "exception occurred: %s\n", cstr.getStr() );
1176 throw;
1179 return bRet ? 0 : 1;
1182 // XServiceInfo
1184 OUString TestBridgeImpl::getImplementationName()
1186 return IMPLNAME;
1189 sal_Bool TestBridgeImpl::supportsService( const OUString & rServiceName )
1191 return cppu::supportsService(this, rServiceName);
1194 Sequence< OUString > TestBridgeImpl::getSupportedServiceNames()
1196 return bridge_test::getSupportedServiceNames();
1200 static Reference< XInterface > TestBridgeImpl_create(
1201 const Reference< XComponentContext > & xContext )
1203 return Reference< XInterface >(
1204 static_cast< OWeakObject * >( new TestBridgeImpl( xContext ) ) );
1209 extern "C"
1212 SAL_DLLPUBLIC_EXPORT void * component_getFactory(
1213 const sal_Char * pImplName, void * pServiceManager,
1214 SAL_UNUSED_PARAMETER void * )
1216 void * pRet = nullptr;
1218 if (pServiceManager && rtl_str_compare( pImplName, IMPLNAME ) == 0)
1220 Reference< XInterface > xFactory(
1221 createSingleComponentFactory(
1222 bridge_test::TestBridgeImpl_create,
1223 IMPLNAME,
1224 bridge_test::getSupportedServiceNames() ) );
1226 if (xFactory.is())
1228 xFactory->acquire();
1229 pRet = xFactory.get();
1233 return pRet;
1237 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */