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 <com/sun/star/test/XSimpleTest.hpp>
21 #include <com/sun/star/io/XActiveDataSink.hpp>
22 #include <com/sun/star/io/XActiveDataSource.hpp>
23 #include <com/sun/star/io/XMarkableStream.hpp>
24 #include <com/sun/star/io/XConnectable.hpp>
26 #include <com/sun/star/lang/XServiceInfo.hpp>
28 #include <cppuhelper/factory.hxx>
29 #include <cppuhelper/implbase.hxx>
31 #include <osl/conditn.hxx>
33 using namespace ::osl
;
34 using namespace ::cppu
;
35 using namespace ::com::sun::star::uno
;
36 using namespace ::com::sun::star::io
;
37 using namespace ::com::sun::star::lang
;
38 using namespace ::com::sun::star::test
;
41 #include "testfactreg.hxx"
44 class OMarkableOutputStreamTest
: public WeakImplHelper
< XSimpleTest
>
47 explicit OMarkableOutputStreamTest( const Reference
< XMultiServiceFactory
> & rFactory
);
48 ~OMarkableOutputStreamTest();
50 public: // implementation names
51 static Sequence
< OUString
> getSupportedServiceNames_Static() throw ();
52 static OUString
getImplementationName_Static() throw ();
55 virtual void SAL_CALL
testInvariant(
56 const OUString
& TestName
,
57 const Reference
< XInterface
>& TestObject
)
58 throw ( IllegalArgumentException
,
61 virtual sal_Int32 SAL_CALL
test( const OUString
& TestName
,
62 const Reference
< XInterface
>& TestObject
,
63 sal_Int32 hTestHandle
)
64 throw ( IllegalArgumentException
, RuntimeException
);
65 virtual sal_Bool SAL_CALL
testPassed()
66 throw ( RuntimeException
);
67 virtual Sequence
< OUString
> SAL_CALL
getErrors()
68 throw (RuntimeException
);
69 virtual Sequence
< Any
> SAL_CALL
getErrorExceptions()
70 throw (RuntimeException
);
71 virtual Sequence
< OUString
> SAL_CALL
getWarnings()
72 throw (RuntimeException
);
75 void testSimple( const Reference
< XOutputStream
> &r
, const Reference
< XInputStream
> &rInput
);
78 Sequence
<Any
> m_seqExceptions
;
79 Sequence
<OUString
> m_seqErrors
;
80 Sequence
<OUString
> m_seqWarnings
;
81 Reference
< XMultiServiceFactory
> m_rFactory
;
85 OMarkableOutputStreamTest::OMarkableOutputStreamTest( const Reference
< XMultiServiceFactory
> &rFactory
)
86 : m_rFactory( rFactory
)
91 OMarkableOutputStreamTest::~OMarkableOutputStreamTest()
97 void OMarkableOutputStreamTest::testInvariant( const OUString
& TestName
,
98 const Reference
< XInterface
>& TestObject
)
99 throw ( IllegalArgumentException
, RuntimeException
)
101 Reference
< XServiceInfo
> info( TestObject
, UNO_QUERY
);
102 ERROR_ASSERT( info
.is() , "XServiceInfo not supported !" );
105 ERROR_ASSERT( info
->supportsService( TestName
), "XServiceInfo test failed" );
106 ERROR_ASSERT( ! info
->supportsService(
107 OUString( "bla bluzb") ) , "XServiceInfo test failed" );
112 sal_Int32
OMarkableOutputStreamTest::test(
113 const OUString
& TestName
,
114 const Reference
< XInterface
>& TestObject
,
115 sal_Int32 hTestHandle
)
116 throw ( IllegalArgumentException
, RuntimeException
)
118 if( OUString( "com.sun.star.io.MarkableOutputStream" )
122 if( 0 == hTestHandle
)
124 testInvariant( TestName
, TestObject
);
128 Reference
< XInterface
> x
= m_rFactory
->createInstance("com.sun.star.io.Pipe");
129 Reference
< XOutputStream
> rPipeOutput( x
, UNO_QUERY
);
130 Reference
< XInputStream
> rPipeInput( x
, UNO_QUERY
);
132 Reference
< XActiveDataSource
> source( TestObject
, UNO_QUERY
);
133 source
->setOutputStream( rPipeOutput
);
135 Reference
< XOutputStream
> rOutput( TestObject
, UNO_QUERY
);
137 OSL_ASSERT( rPipeInput
.is() );
138 OSL_ASSERT( rOutput
.is() );
139 if( 1 == hTestHandle
) {
140 // checks usual streaming
141 testSimple( rOutput
, rPipeInput
);
146 catch( const Exception
&e
)
148 OString o
= OUStringToOString( e
.Message
, RTL_TEXTENCODING_ASCII_US
);
149 BUILD_ERROR( 0 , o
.getStr() );
153 BUILD_ERROR( 0 , "unknown exception (Exception is not base class)" );
158 if( 2 == hTestHandle
)
160 // all tests finished.
165 throw IllegalArgumentException();
171 sal_Bool
OMarkableOutputStreamTest::testPassed() throw (RuntimeException
)
173 return m_seqErrors
.getLength() == 0;
177 Sequence
< OUString
> OMarkableOutputStreamTest::getErrors() throw (RuntimeException
)
183 Sequence
< Any
> OMarkableOutputStreamTest::getErrorExceptions() throw (RuntimeException
)
185 return m_seqExceptions
;
189 Sequence
< OUString
> OMarkableOutputStreamTest::getWarnings() throw (RuntimeException
)
191 return m_seqWarnings
;
195 void OMarkableOutputStreamTest::testSimple( const Reference
< XOutputStream
> &rOutput
,
196 const Reference
< XInputStream
> &rInput
)
198 Reference
< XMarkableStream
> rMarkable( rOutput
, UNO_QUERY
);
200 ERROR_ASSERT( rMarkable
.is() , "no MarkableStream implemented" );
202 // first check normal input/output facility
203 char pcStr
[] = "Live long and prosper !";
205 Sequence
<sal_Int8
> seqWrite( strlen( pcStr
)+1 );
206 memcpy( seqWrite
.getArray() , pcStr
, seqWrite
.getLength() );
208 Sequence
<sal_Int8
> seqRead( seqWrite
.getLength() );
212 for( i
= 0 ; i
< nMax
; i
++ ) {
213 rOutput
->writeBytes( seqWrite
);
214 rInput
->readBytes( seqRead
, rInput
->available() );
215 ERROR_ASSERT( ! strcmp( (char *) seqWrite
.getArray() , (char * )seqRead
.getArray() ) ,
216 "error during read/write/skip" );
219 // Check buffer resizing
221 for( i
= 0 ; i
< nMax
; i
++ ) {
222 rOutput
->writeBytes( seqWrite
);
225 for( i
= 0 ; i
< nMax
; i
++ ) {
226 rInput
->readBytes( seqRead
, seqWrite
.getLength() );
227 ERROR_ASSERT( ! strcmp( (char *) seqWrite
.getArray() , (char * )seqRead
.getArray() ) ,
228 "error during read/write" );
231 // Check creating marks !
232 sal_Int32 nMark
= rMarkable
->createMark();
234 for( i
= 0 ; i
< nMax
; i
++ ) {
235 rOutput
->writeBytes( seqWrite
);
238 ERROR_ASSERT( 0 == rInput
->available() , "bytes available though mark is holded" );
240 ERROR_ASSERT( nMax
*seqWrite
.getLength() == rMarkable
->offsetToMark( nMark
) ,
241 "offsetToMark failure" );
243 rMarkable
->deleteMark( nMark
);
244 ERROR_ASSERT( nMax
*seqWrite
.getLength() == rInput
->available(),"bytes are not available though mark has been deleted" );
246 rInput
->skipBytes( nMax
*seqWrite
.getLength() );
247 ERROR_ASSERT( 0 == rInput
->available(), "skip bytes failure" );
251 rMarkable
->jumpToMark( nMark
);
252 ERROR_ASSERT( 0 , "jump to non existing mark possible !" );
254 catch ( IllegalArgumentException
& )
256 // ok, exception was thrown
259 // test putting marks not at the end of the stream!
260 ERROR_ASSERT( 0 == rInput
->available(), "stream isn't clean" );
262 Sequence
< sal_Int8
> aByte(256);
264 for( i
= 0 ; i
< 256 ; i
++ )
266 aByte
.getArray()[i
] = i
;
268 sal_Int32 nMark1
= rMarkable
->createMark();
270 rOutput
->writeBytes( aByte
);
271 rMarkable
->jumpToMark( nMark1
);
273 rOutput
->writeBytes( aByte
);
275 sal_Int32 nMark2
= rMarkable
->createMark( );
277 for( i
= 0 ; i
< 10 ; i
++ )
279 aByte
.getArray()[i
] = i
+10;
282 rOutput
->writeBytes( aByte
);
284 // allow the bytes to be written !
285 rMarkable
->jumpToFurthest();
286 rMarkable
->deleteMark( nMark1
);
287 rMarkable
->deleteMark( nMark2
);
289 ERROR_ASSERT( 256 == rInput
->available(), "in between mark failure" );
290 rInput
->readBytes( aByte
,256);
291 for( i
= 0 ; i
< 256 ; i
++ )
293 ERROR_ASSERT( i
== ((sal_uInt8
*)(aByte
.getArray()))[i
] , "in between mark failure" );
298 // now a more extensive mark test !
299 Sequence
<sal_Int8
> as
[4];
302 for( i
= 0 ; i
< 4 ; i
++ ) {
304 as
[i
].getArray()[0] = i
;
305 an
[i
] = rMarkable
->createMark();
306 rOutput
->writeBytes( as
[i
] );
309 // check offset to mark
310 for( i
= 0 ; i
< 4 ; i
++ ) {
311 ERROR_ASSERT( rMarkable
->offsetToMark( an
[i
] ) == 4-i
, "offsetToMark failure" );
314 rMarkable
->jumpToMark( an
[1] );
315 ERROR_ASSERT( rMarkable
->offsetToMark( an
[3] ) == -2 , "offsetToMark failure" );
317 rMarkable
->jumpToFurthest( );
318 ERROR_ASSERT( rMarkable
->offsetToMark( an
[0] ) == 4 , "offsetToMark failure" );
320 // now do a rewrite !
321 for( i
= 0 ; i
< 4 ; i
++ ) {
322 rMarkable
->jumpToMark( an
[3-i
] );
323 rOutput
->writeBytes( as
[i
] );
325 // NOTE : CursorPos 1
327 // now delete the marks !
328 for( i
= 0 ; i
< 4 ; i
++ ) {
329 rMarkable
->deleteMark( an
[i
] );
331 ERROR_ASSERT( rInput
->available() == 1 , "wrong number of bytes flushed" );
333 rMarkable
->jumpToFurthest();
335 ERROR_ASSERT( rInput
->available() == 4 , "wrong number of bytes flushed" );
337 rInput
->readBytes( seqRead
, 4 );
339 ERROR_ASSERT( 3 == seqRead
.getArray()[0] , "rewrite didn't work" );
340 ERROR_ASSERT( 2 == seqRead
.getArray()[1] , "rewrite didn't work" );
341 ERROR_ASSERT( 1 == seqRead
.getArray()[2] , "rewrite didn't work" );
342 ERROR_ASSERT( 0 == seqRead
.getArray()[3] , "rewrite didn't work" );
344 rOutput
->closeOutput();
345 rInput
->closeInput();
357 * for external binding
361 Reference
< XInterface
> SAL_CALL
OMarkableOutputStreamTest_CreateInstance( const Reference
< XMultiServiceFactory
> & rSMgr
) throw(Exception
)
363 OMarkableOutputStreamTest
*p
= new OMarkableOutputStreamTest( rSMgr
);
364 return Reference
< XInterface
> ( (static_cast< OWeakObject
* >(p
)) );
368 Sequence
<OUString
> OMarkableOutputStreamTest_getSupportedServiceNames() throw ()
370 Sequence
<OUString
> aRet
{ OMarkableOutputStreamTest_getImplementationName() };
375 OUString
OMarkableOutputStreamTest_getServiceName() throw ()
377 return OUString( "test.com.sun.star.io.MarkableOutputStream");
380 OUString
OMarkableOutputStreamTest_getImplementationName() throw ()
382 return OUString( "test.com.sun.starextensions.stm.MarkableOutputStream");
389 class OMarkableInputStreamTest
: public WeakImplHelper
< XSimpleTest
>
392 explicit OMarkableInputStreamTest( const Reference
< XMultiServiceFactory
> & rFactory
);
393 ~OMarkableInputStreamTest();
395 public: // implementation names
396 static Sequence
< OUString
> getSupportedServiceNames_Static() throw () ;
397 static OUString
getImplementationName_Static() throw () ;
400 virtual void SAL_CALL
testInvariant(
401 const OUString
& TestName
,
402 const Reference
< XInterface
>& TestObject
)
403 throw ( IllegalArgumentException
, RuntimeException
) ;
405 virtual sal_Int32 SAL_CALL
test(
406 const OUString
& TestName
,
407 const Reference
< XInterface
>& TestObject
,
408 sal_Int32 hTestHandle
)
409 throw ( IllegalArgumentException
,
412 virtual sal_Bool SAL_CALL
testPassed()
413 throw ( RuntimeException
);
414 virtual Sequence
< OUString
> SAL_CALL
getErrors()
415 throw (RuntimeException
);
416 virtual Sequence
< Any
> SAL_CALL
getErrorExceptions()
417 throw (RuntimeException
);
418 virtual Sequence
< OUString
> SAL_CALL
getWarnings()
419 throw (RuntimeException
);
422 void testSimple( const Reference
< XOutputStream
> &r
,
423 const Reference
< XInputStream
> &rInput
);
426 Sequence
<Any
> m_seqExceptions
;
427 Sequence
<OUString
> m_seqErrors
;
428 Sequence
<OUString
> m_seqWarnings
;
429 Reference
< XMultiServiceFactory
> m_rFactory
;
433 OMarkableInputStreamTest::OMarkableInputStreamTest( const Reference
< XMultiServiceFactory
> &rFactory
)
434 : m_rFactory( rFactory
)
439 OMarkableInputStreamTest::~OMarkableInputStreamTest()
445 void OMarkableInputStreamTest::testInvariant(
446 const OUString
& TestName
, const Reference
< XInterface
>& TestObject
)
447 throw ( IllegalArgumentException
, RuntimeException
)
449 if( OUString( "com.sun.star.io.MarkableInputStream")
451 Reference
<XServiceInfo
> info( TestObject
, UNO_QUERY
);
452 ERROR_ASSERT( info
.is() , "XServiceInfo not supported !" );
455 ERROR_ASSERT( info
->supportsService( TestName
), "XServiceInfo test failed" );
457 ! info
->supportsService(
458 OUString("bla bluzb") ) ,
459 "XServiceInfo test failed" );
464 throw IllegalArgumentException();
469 sal_Int32
OMarkableInputStreamTest::test(
470 const OUString
& TestName
,
471 const Reference
< XInterface
>& TestObject
,
472 sal_Int32 hTestHandle
) throw ( IllegalArgumentException
, RuntimeException
)
474 if( OUString( "com.sun.star.io.MarkableInputStream") == TestName
)
478 if( 0 == hTestHandle
) {
479 testInvariant( TestName
, TestObject
);
482 Reference
< XInterface
> x
= m_rFactory
->createInstance("com.sun.star.io.Pipe");
483 Reference
< XOutputStream
> rPipeOutput( x
, UNO_QUERY
);
484 Reference
< XInputStream
> rPipeInput( x
, UNO_QUERY
);
486 Reference
< XActiveDataSink
> sink( TestObject
, UNO_QUERY
);
487 sink
->setInputStream( rPipeInput
);
489 Reference
< XInputStream
> rInput( TestObject
, UNO_QUERY
);
491 OSL_ASSERT( rPipeOutput
.is() );
492 OSL_ASSERT( rInput
.is() );
493 if( 1 == hTestHandle
) {
494 // checks usual streaming
495 testSimple( rPipeOutput
, rInput
);
500 catch( const Exception
& e
)
502 OString o
= OUStringToOString( e
.Message
, RTL_TEXTENCODING_ASCII_US
);
503 BUILD_ERROR( 0 , o
.getStr() );
507 BUILD_ERROR( 0 , "unknown exception (Exception is not base class)" );
512 if( 2 == hTestHandle
) {
513 // all tests finished.
519 throw IllegalArgumentException();
525 sal_Bool
OMarkableInputStreamTest::testPassed() throw (RuntimeException
)
527 return m_seqErrors
.getLength() == 0;
531 Sequence
< OUString
> OMarkableInputStreamTest::getErrors() throw (RuntimeException
)
537 Sequence
< Any
> OMarkableInputStreamTest::getErrorExceptions() throw (RuntimeException
)
539 return m_seqExceptions
;
543 Sequence
< OUString
> OMarkableInputStreamTest::getWarnings() throw (RuntimeException
)
545 return m_seqWarnings
;
549 void OMarkableInputStreamTest::testSimple( const Reference
< XOutputStream
> &rOutput
,
550 const Reference
< XInputStream
> &rInput
)
552 Reference
< XMarkableStream
> rMarkable( rInput
, UNO_QUERY
);
554 Sequence
<sal_Int8
> seqWrite( 256 );
555 Sequence
<sal_Int8
> seqRead(10);
557 for( int i
= 0 ; i
< 256 ; i
++ )
559 seqWrite
.getArray()[i
] = i
;
562 rOutput
->writeBytes( seqWrite
);
563 ERROR_ASSERT( 256 == rInput
->available() , "basic read/write failure" );
565 rInput
->readBytes( seqRead
, 10 );
566 ERROR_ASSERT( 9 == seqRead
.getArray()[9] , "basic read/write failure" );
568 sal_Int32 nMark
= rMarkable
->createMark();
570 rInput
->skipBytes( 50 );
571 ERROR_ASSERT( 256-10-50 == rInput
->available() , "marking error" );
572 ERROR_ASSERT( 50 == rMarkable
->offsetToMark( nMark
) , "marking error" );
574 rMarkable
->jumpToMark( nMark
);
575 ERROR_ASSERT( 256-10 == rInput
->available() , "marking error" );
577 rInput
->readBytes( seqRead
, 10 );
578 ERROR_ASSERT( 10 == seqRead
.getArray()[0] , "marking error" );
582 sal_Int32 nInBetweenMark
= rMarkable
->createMark( );
583 rMarkable
->jumpToMark( nMark
);
584 rMarkable
->jumpToMark( nInBetweenMark
);
586 rInput
->readBytes( seqRead
, 10 );
587 ERROR_ASSERT( 20 == seqRead
.getArray()[0] , "Inbetween mark failed!\n" );
589 rMarkable
->deleteMark( nMark
);
591 // Check if releasing the first bytes works correct.
592 rMarkable
->jumpToMark( nInBetweenMark
);
593 rInput
->readBytes( seqRead
, 10 );
594 ERROR_ASSERT( 20 == seqRead
.getArray()[0] , "Inbetween mark failed!\n" );
596 rMarkable
->deleteMark( nInBetweenMark
);
599 rMarkable
->jumpToFurthest();
600 ERROR_ASSERT( 256-10-50 == rInput
->available() , "marking error" );
603 ERROR_ASSERT( 100 == rInput
->readSomeBytes( seqRead
, 100 ) , "wrong results using readSomeBytes" );
604 ERROR_ASSERT( 96 == rInput
->readSomeBytes( seqRead
, 1000) , "wrong results using readSomeBytes" );
605 rOutput
->closeOutput();
606 rInput
->closeInput();
616 * for external binding
620 Reference
< XInterface
> SAL_CALL
OMarkableInputStreamTest_CreateInstance( const Reference
< XMultiServiceFactory
> & rSMgr
) throw(Exception
)
622 OMarkableInputStreamTest
*p
= new OMarkableInputStreamTest( rSMgr
);
623 return Reference
< XInterface
> ( (static_cast< OWeakObject
* >(p
)) );
627 Sequence
<OUString
> OMarkableInputStreamTest_getSupportedServiceNames() throw ()
629 Sequence
<OUString
> aRet
{ OMarkableInputStreamTest_getImplementationName() };
634 OUString
OMarkableInputStreamTest_getServiceName() throw ()
636 return OUString( "test.com.sun.star.io.MarkableInputStream");
639 OUString
OMarkableInputStreamTest_getImplementationName() throw ()
641 return OUString( "test.com.sun.star.extensions.stm.MarkableInputStream" );
644 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */