Line 0
Link Here
|
|
|
1 |
/************************************************************** |
2 |
* |
3 |
* Licensed to the Apache Software Foundation (ASF) under one |
4 |
* or more contributor license agreements. See the NOTICE file |
5 |
* distributed with this work for additional information |
6 |
* regarding copyright ownership. The ASF licenses this file |
7 |
* to you under the Apache License, Version 2.0 (the |
8 |
* "License"); you may not use this file except in compliance |
9 |
* with the License. You may obtain a copy of the License at |
10 |
* |
11 |
* http://www.apache.org/licenses/LICENSE-2.0 |
12 |
* |
13 |
* Unless required by applicable law or agreed to in writing, |
14 |
* software distributed under the License is distributed on an |
15 |
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
16 |
* KIND, either express or implied. See the License for the |
17 |
* specific language governing permissions and limitations |
18 |
* under the License. |
19 |
* |
20 |
*************************************************************/ |
21 |
|
22 |
|
23 |
|
24 |
// MARKER(update_precomp.py): autogen include statement, do not remove |
25 |
#include "precompiled_extensions.hxx" |
26 |
#include <com/sun/star/lang/XMultiServiceFactory.hpp> |
27 |
#include <com/sun/star/lang/XSingleServiceFactory.hpp> |
28 |
#include <com/sun/star/loader/XImplementationLoader.hpp> |
29 |
#include <com/sun/star/loader/CannotActivateFactoryException.hpp> |
30 |
|
31 |
#include <plugin/impl.hxx> |
32 |
#include <tools/fsys.hxx> |
33 |
#include <ucbhelper/content.hxx> |
34 |
#include <tools/urlobj.hxx> |
35 |
#include <tools/string.hxx> |
36 |
#include <vcl/svapp.hxx> |
37 |
#include <vos/timer.hxx> |
38 |
#include <osl/file.hxx> |
39 |
|
40 |
#ifdef UNX |
41 |
#include <sys/types.h> |
42 |
#include <sys/socket.h> |
43 |
#endif |
44 |
|
45 |
#if OSL_DEBUG_LEVEL > 1 |
46 |
#include <stdio.h> |
47 |
#endif |
48 |
|
49 |
using namespace com::sun::star; |
50 |
using namespace com::sun::star::io; |
51 |
using namespace com::sun::star::beans; |
52 |
using namespace com::sun::star::plugin; |
53 |
using namespace rtl; |
54 |
using namespace osl; |
55 |
|
56 |
class PluginDisposer : public vos::OTimer |
57 |
{ |
58 |
private: |
59 |
XPlugin_Impl* m_pPlugin; |
60 |
|
61 |
virtual void SAL_CALL onShot(); |
62 |
public: |
63 |
PluginDisposer( XPlugin_Impl* pPlugin ) : |
64 |
OTimer( vos::TTimeValue( 2, 0 ), |
65 |
vos::TTimeValue( 2, 0 ) ), |
66 |
m_pPlugin( pPlugin ) |
67 |
{ start(); } |
68 |
~PluginDisposer() {} |
69 |
}; |
70 |
|
71 |
void PluginDisposer::onShot() |
72 |
{ |
73 |
if( m_pPlugin ) |
74 |
{ |
75 |
if( m_pPlugin->isDisposable() ) |
76 |
{ |
77 |
sal_uLong nEvent; |
78 |
Application::PostUserEvent( nEvent, LINK( m_pPlugin, XPlugin_Impl, secondLevelDispose ), (void*)m_pPlugin ); |
79 |
} |
80 |
} |
81 |
else |
82 |
release(); |
83 |
} |
84 |
|
85 |
//================================================================================================== |
86 |
|
87 |
Any XPlugin_Impl::queryInterface( const Type& type ) throw( RuntimeException ) |
88 |
{ |
89 |
return OWeakAggObject::queryInterface( type ); |
90 |
} |
91 |
|
92 |
Any XPlugin_Impl::queryAggregation( const Type& type ) throw( RuntimeException ) |
93 |
{ |
94 |
Any aRet( cppu::queryInterface( type, static_cast< XPlugin* >(this) ) ); |
95 |
if( ! aRet.hasValue() ) |
96 |
aRet = PluginControl_Impl::queryAggregation( type ); |
97 |
return aRet; |
98 |
} |
99 |
|
100 |
|
101 |
XPlugin_Impl::XPlugin_Impl( const uno::Reference< com::sun::star::uno::XComponentContext > & rxContext) : |
102 |
PluginControl_Impl(), |
103 |
m_xContext( rxContext ), |
104 |
m_pPluginComm( NULL ), |
105 |
m_aEncoding( gsl_getSystemTextEncoding() ), |
106 |
m_pArgv( NULL ), |
107 |
m_pArgn( NULL ), |
108 |
m_nArgs( 0 ), |
109 |
m_aPluginMode( NP_FULL ), |
110 |
m_nProvidingState( PROVIDING_NONE ), |
111 |
m_nCalledFromPlugin( 0 ), |
112 |
m_pDisposer( NULL ), |
113 |
m_bIsDisposed( sal_False ) |
114 |
{ |
115 |
memset( &m_aInstance, 0, sizeof( m_aInstance ) ); |
116 |
memset( &m_aNPWindow, 0, sizeof( m_aNPWindow ) ); |
117 |
memset( &m_aSysPlugData, 0, sizeof( m_aSysPlugData ) ); |
118 |
|
119 |
m_xModel = new PluginModel(); |
120 |
uno::Reference< com::sun::star::beans::XPropertySet > xPS( m_xModel, UNO_QUERY ); |
121 |
xPS->addPropertyChangeListener( OUString(), this ); |
122 |
|
123 |
Guard< Mutex > aGuard( PluginManager::get().getPluginMutex() ); |
124 |
PluginManager::get().getPlugins().push_back( this ); |
125 |
} |
126 |
|
127 |
void XPlugin_Impl::destroyInstance() |
128 |
{ |
129 |
Guard< Mutex > aGuard( m_aMutex ); |
130 |
|
131 |
NPSavedData* pSavedData = NULL; |
132 |
|
133 |
destroyStreams(); |
134 |
if( getPluginComm() ) |
135 |
{ |
136 |
getPluginComm()->NPP_Destroy( this, &pSavedData ); |
137 |
getPluginComm()->decRef(); |
138 |
m_pPluginComm = NULL; |
139 |
} |
140 |
|
141 |
freeArgs(); |
142 |
|
143 |
while( m_aPEventListeners.size() ) |
144 |
{ |
145 |
delete *m_aPEventListeners.begin(); |
146 |
m_aPEventListeners.pop_front(); |
147 |
} |
148 |
} |
149 |
|
150 |
XPlugin_Impl::~XPlugin_Impl() |
151 |
{ |
152 |
destroyInstance(); |
153 |
} |
154 |
|
155 |
void XPlugin_Impl::checkListeners( const char* normalizedURL ) |
156 |
{ |
157 |
if( ! normalizedURL ) |
158 |
return; |
159 |
|
160 |
Guard< Mutex > aGuard( m_aMutex ); |
161 |
|
162 |
std::list<PluginEventListener*>::iterator iter; |
163 |
for( iter = m_aPEventListeners.begin(); |
164 |
iter != m_aPEventListeners.end(); |
165 |
++iter ) |
166 |
{ |
167 |
if( ! strcmp( normalizedURL, (*iter)->getURL() ) || |
168 |
! strcmp( normalizedURL, (*iter)->getNormalizedURL() ) ) |
169 |
{ |
170 |
(*iter)->disposing( com::sun::star::lang::EventObject() ); |
171 |
delete *iter; |
172 |
m_aPEventListeners.remove( *iter ); |
173 |
return; |
174 |
} |
175 |
} |
176 |
} |
177 |
|
178 |
IMPL_LINK( XPlugin_Impl, secondLevelDispose, XPlugin_Impl*, /*pThis*/ ) |
179 |
{ |
180 |
Guard< Mutex > aGuard( m_aMutex ); |
181 |
|
182 |
// may have become undisposable between PostUserEvent and here |
183 |
// or may have disposed and receive a second UserEvent |
184 |
std::list<XPlugin_Impl*>& rList = PluginManager::get().getPlugins(); |
185 |
std::list<XPlugin_Impl*>::iterator iter; |
186 |
|
187 |
{ |
188 |
Guard< Mutex > aPluginGuard( PluginManager::get().getPluginMutex() ); |
189 |
for( iter = rList.begin(); iter != rList.end(); ++iter ) |
190 |
{ |
191 |
if( *iter == this ) |
192 |
break; |
193 |
} |
194 |
if( iter == rList.end() || ! isDisposable() ) |
195 |
return 0; |
196 |
} |
197 |
|
198 |
if (m_pDisposer) |
199 |
{ |
200 |
m_pDisposer->release(); |
201 |
m_pDisposer = NULL; |
202 |
} |
203 |
|
204 |
uno::Reference< XPlugin > xProtection( this ); |
205 |
uno::Reference< com::sun::star::beans::XPropertySet > xPS( m_xModel, UNO_QUERY ); |
206 |
xPS->removePropertyChangeListener( OUString(), this ); |
207 |
{ |
208 |
Guard< Mutex > aPluginGuard( PluginManager::get().getPluginMutex() ); |
209 |
rList.remove( this ); |
210 |
} |
211 |
m_aNPWindow.window = NULL; |
212 |
#ifndef UNX |
213 |
// acrobat does an unconditional XtParent on the windows widget |
214 |
getPluginComm()->NPP_SetWindow( this ); |
215 |
#endif |
216 |
destroyInstance(); |
217 |
PluginControl_Impl::dispose(); |
218 |
return 0; |
219 |
} |
220 |
|
221 |
void XPlugin_Impl::dispose() throw() |
222 |
{ |
223 |
Guard< Mutex > aGuard( m_aMutex ); |
224 |
|
225 |
if (m_bIsDisposed || !getPluginComm()) |
226 |
return; |
227 |
m_bIsDisposed = sal_True; |
228 |
|
229 |
if( isDisposable() ) |
230 |
secondLevelDispose( this ); |
231 |
else |
232 |
{ |
233 |
m_pDisposer = new PluginDisposer( this ); |
234 |
m_pDisposer->acquire(); |
235 |
} |
236 |
} |
237 |
|
238 |
void XPlugin_Impl::initArgs( const Sequence< OUString >& argn, |
239 |
const Sequence< OUString >& argv, |
240 |
sal_Int16 mode ) |
241 |
{ |
242 |
m_aPluginMode = mode; |
243 |
|
244 |
m_nArgs = argn.getLength(); |
245 |
m_pArgn = new const char*[m_nArgs]; |
246 |
m_pArgv = new const char*[m_nArgs]; |
247 |
const OUString* pUArgn = argn.getConstArray(); |
248 |
const OUString* pUArgv = argv.getConstArray(); |
249 |
for( int i = 0; i < m_nArgs; i++ ) |
250 |
{ |
251 |
m_pArgn[i] = strdup( |
252 |
OUStringToOString( pUArgn[i], m_aEncoding ).getStr() |
253 |
); |
254 |
m_pArgv[i] = strdup( |
255 |
OUStringToOString( pUArgv[i], m_aEncoding ).getStr() |
256 |
); |
257 |
} |
258 |
} |
259 |
|
260 |
void XPlugin_Impl::freeArgs() |
261 |
{ |
262 |
if( m_nArgs > 0 ) |
263 |
{ |
264 |
for( ; m_nArgs--; ) |
265 |
{ |
266 |
free( (void*)m_pArgn[m_nArgs] ); |
267 |
free( (void*)m_pArgv[m_nArgs] ); |
268 |
} |
269 |
delete [] m_pArgn; |
270 |
delete [] m_pArgv; |
271 |
} |
272 |
} |
273 |
|
274 |
void XPlugin_Impl::prependArg( const char* pName, const char* pValue ) |
275 |
{ |
276 |
const char** pNewNames = new const char*[m_nArgs+1]; |
277 |
const char** pNewValues = new const char*[m_nArgs+1]; |
278 |
|
279 |
pNewNames[0] = strdup( pName ); |
280 |
pNewValues[0] = strdup( pValue ); |
281 |
for( int nIndex = 0; nIndex < m_nArgs; ++nIndex ) |
282 |
{ |
283 |
pNewNames[nIndex+1] = m_pArgn[nIndex]; |
284 |
pNewValues[nIndex+1]= m_pArgv[nIndex]; |
285 |
} |
286 |
// free old arrays |
287 |
delete [] m_pArgn; |
288 |
delete [] m_pArgv; |
289 |
// set new arrays |
290 |
m_pArgn = pNewNames; |
291 |
m_pArgv = pNewValues; |
292 |
// set new number of arguments |
293 |
m_nArgs++; |
294 |
#if OSL_DEBUG_LEVEL > 1 |
295 |
fprintf( stderr, "inserted %s=%s\n", pNewNames[0], pNewValues[0] ); |
296 |
#endif |
297 |
} |
298 |
|
299 |
void XPlugin_Impl::handleSpecialArgs() |
300 |
{ |
301 |
// special handling for real audio which needs a lot of parameters |
302 |
// or won't function at all |
303 |
if( ! m_aDescription.Mimetype.compareToAscii( "audio/x-pn-realaudio-plugin" ) && m_nArgs < 1 ) |
304 |
{ |
305 |
OUString aURL; |
306 |
if( m_xModel.is() ) |
307 |
{ |
308 |
try |
309 |
{ |
310 |
uno::Reference< XPropertySet > xProp( m_xModel, UNO_QUERY ); |
311 |
Any aProp = xProp->getPropertyValue( OUString( RTL_CONSTASCII_USTRINGPARAM( "URL" ) ) ); |
312 |
aProp >>= aURL; |
313 |
} |
314 |
catch( UnknownPropertyException ) |
315 |
{ |
316 |
} |
317 |
} |
318 |
|
319 |
if( aURL.getLength() ) |
320 |
{ |
321 |
// set new args, old args need not be freed as there were none set |
322 |
m_nArgs = 6; |
323 |
m_pArgn = new const char*[m_nArgs]; |
324 |
m_pArgv = new const char*[m_nArgs]; |
325 |
|
326 |
// SRC |
327 |
m_pArgn[0] = strdup( "SRC" ); |
328 |
m_pArgv[0] = strdup( OUStringToOString( aURL, m_aEncoding ).getStr() ); |
329 |
// WIDTH |
330 |
m_pArgn[1] = strdup( "WIDTH" ); |
331 |
m_pArgv[1] = strdup( "200" ); |
332 |
// HEIGHT |
333 |
m_pArgn[2] = strdup( "HEIGHT" ); |
334 |
m_pArgv[2] = strdup( "200" ); |
335 |
// CONTROLS |
336 |
m_pArgn[3] = strdup( "CONTROLS" ); |
337 |
m_pArgv[3] = strdup( "PlayButton,StopButton,ImageWindow" ); |
338 |
// AUTOSTART |
339 |
m_pArgn[4] = strdup( "AUTOSTART" ); |
340 |
m_pArgv[4] = strdup( "TRUE" ); |
341 |
// NOJAVA |
342 |
m_pArgn[5] = strdup( "NOJAVA" ); |
343 |
m_pArgv[5] = strdup( "TRUE" ); |
344 |
} |
345 |
} |
346 |
// #69333# special for pdf |
347 |
else if( ! m_aDescription.Mimetype.compareToAscii( "application/pdf" ) ) |
348 |
m_aPluginMode = PluginMode::FULL; |
349 |
|
350 |
// see if we have a TYPE tag |
351 |
int nIndex; |
352 |
for( nIndex = 0; nIndex < m_nArgs; ++nIndex ) |
353 |
if( m_pArgn[nIndex][0] == 'T' && |
354 |
m_pArgn[nIndex][1] == 'Y' && |
355 |
m_pArgn[nIndex][2] == 'P' && |
356 |
m_pArgn[nIndex][3] == 'E' && |
357 |
m_pArgn[nIndex][4] == 0 ) |
358 |
break; |
359 |
if( nIndex >= m_nArgs ) |
360 |
{ |
361 |
// TYPE |
362 |
prependArg( "TYPE", OUStringToOString( m_aDescription.Mimetype, m_aEncoding ).getStr() ); |
363 |
} |
364 |
|
365 |
// see if we have a SRC tag |
366 |
for( nIndex = 0; nIndex < m_nArgs; ++nIndex ) |
367 |
if( m_pArgn[nIndex][0] == 'S' && |
368 |
m_pArgn[nIndex][1] == 'R' && |
369 |
m_pArgn[nIndex][2] == 'C' && |
370 |
m_pArgn[nIndex][3] == 0 ) |
371 |
break; |
372 |
if( nIndex >= m_nArgs ) |
373 |
{ |
374 |
// need a SRC parameter (as all browser set one on the plugin |
375 |
OUString aURL; |
376 |
if( m_xModel.is() ) |
377 |
{ |
378 |
try |
379 |
{ |
380 |
uno::Reference< XPropertySet > xProp( m_xModel, UNO_QUERY ); |
381 |
Any aProp = xProp->getPropertyValue( OUString( RTL_CONSTASCII_USTRINGPARAM( "URL" ) ) ); |
382 |
aProp >>= aURL; |
383 |
} |
384 |
catch( UnknownPropertyException ) |
385 |
{ |
386 |
} |
387 |
} |
388 |
|
389 |
if( aURL.getLength() ) |
390 |
{ |
391 |
// SRC |
392 |
prependArg( "SRC", OUStringToOString( aURL, m_aEncoding ).getStr() ); |
393 |
} |
394 |
} |
395 |
} |
396 |
|
397 |
void XPlugin_Impl::initInstance( const PluginDescription& rDescription, |
398 |
const Sequence< OUString >& argn, |
399 |
const Sequence< OUString >& argv, |
400 |
sal_Int16 mode ) |
401 |
{ |
402 |
Guard< Mutex > aGuard( m_aMutex ); |
403 |
|
404 |
m_aDescription = rDescription; |
405 |
initArgs( argn, argv, mode ); |
406 |
handleSpecialArgs(); |
407 |
} |
408 |
|
409 |
void XPlugin_Impl::initInstance( const OUString& rURL, |
410 |
const Sequence< OUString >& argn, |
411 |
const Sequence< OUString >& argv, |
412 |
sal_Int16 mode ) |
413 |
{ |
414 |
Guard< Mutex > aGuard( m_aMutex ); |
415 |
|
416 |
initArgs( argn, argv, mode ); |
417 |
m_aDescription = fitDescription( rURL ); |
418 |
|
419 |
m_xModel = new PluginModel( rURL, m_aDescription.Mimetype ); |
420 |
handleSpecialArgs(); |
421 |
} |
422 |
|
423 |
void XPlugin_Impl::modelChanged() |
424 |
{ |
425 |
Guard< Mutex > aGuard( m_aMutex ); |
426 |
|
427 |
m_nProvidingState = PROVIDING_MODEL_UPDATE; |
428 |
|
429 |
destroyInstance(); |
430 |
|
431 |
m_aDescription = fitDescription( getCreationURL() ); |
432 |
if( !m_aDescription.Mimetype.getLength() ) |
433 |
{ |
434 |
m_nProvidingState = PROVIDING_NONE; |
435 |
return; |
436 |
} |
437 |
|
438 |
OUString aURL = getCreationURL(); |
439 |
provideNewStream( m_aDescription.Mimetype, |
440 |
uno::Reference< XActiveDataSource >(), |
441 |
aURL, |
442 |
0, 0, (sal_Bool)(aURL.compareToAscii( "file:", 5 ) == 0) ); |
443 |
m_nProvidingState = PROVIDING_NONE; |
444 |
} |
445 |
|
446 |
OUString XPlugin_Impl::getCreationURL() |
447 |
{ |
448 |
Guard< Mutex > aGuard( m_aMutex ); |
449 |
|
450 |
OUString aRet; |
451 |
uno::Reference< com::sun::star::beans::XPropertySet > xPS( m_xModel, UNO_QUERY ); |
452 |
if( xPS.is() ) |
453 |
{ |
454 |
Any aValue = xPS->getPropertyValue( OUString::createFromAscii( "URL" ) ); |
455 |
aValue >>= aRet; |
456 |
} |
457 |
return aRet; |
458 |
} |
459 |
|
460 |
|
461 |
sal_Bool XPlugin_Impl::setModel( const uno::Reference< com::sun::star::awt::XControlModel > & Model ) |
462 |
throw( RuntimeException ) |
463 |
{ |
464 |
Guard< Mutex > aGuard( m_aMutex ); |
465 |
|
466 |
uno::Reference< com::sun::star::beans::XPropertySet > xPS( Model, UNO_QUERY ); |
467 |
if( ! xPS.is() ) |
468 |
return sal_False; |
469 |
|
470 |
if( getCreationURL().getLength() ) |
471 |
{ |
472 |
m_xModel = Model; |
473 |
modelChanged(); |
474 |
xPS->addPropertyChangeListener( OUString(), this ); |
475 |
return sal_True; |
476 |
} |
477 |
return sal_False; |
478 |
} |
479 |
|
480 |
void XPlugin_Impl::createPeer( const uno::Reference< com::sun::star::awt::XToolkit > & xToolkit, const uno::Reference< com::sun::star::awt::XWindowPeer > & Parent ) |
481 |
throw( RuntimeException ) |
482 |
{ |
483 |
Guard< Mutex > aGuard( m_aMutex ); |
484 |
|
485 |
if( ! _xPeer.is() ) |
486 |
{ |
487 |
if( ! Parent.is() ) |
488 |
throw RuntimeException(); |
489 |
PluginControl_Impl::createPeer( xToolkit, Parent ); |
490 |
} |
491 |
} |
492 |
|
493 |
void XPlugin_Impl::loadPlugin() |
494 |
{ |
495 |
Guard< Mutex > aGuard( m_aMutex ); |
496 |
|
497 |
std::list<PluginComm*>::iterator iter; |
498 |
for( iter = PluginManager::get().getPluginComms().begin(); |
499 |
iter != PluginManager::get().getPluginComms().end(); ++iter ) |
500 |
{ |
501 |
if( OStringToOUString( (*iter)->getLibName(), m_aEncoding ) == m_aDescription.PluginName ) |
502 |
{ |
503 |
setPluginComm( *iter ); |
504 |
break; |
505 |
} |
506 |
} |
507 |
const SystemEnvData* pEnvData = getSysChildSysData(); |
508 |
#if defined( UNX ) && !(defined(QUARTZ)) |
509 |
XSync( (Display*)pEnvData->pDisplay, False ); |
510 |
#endif |
511 |
if( ! getPluginComm() ) |
512 |
{ |
513 |
if( m_aDescription.PluginName.getLength() ) |
514 |
{ |
515 |
#if defined QUARTZ |
516 |
PluginComm* pComm = new MacPluginComm( m_aDescription.Mimetype, |
517 |
m_aDescription.PluginName, |
518 |
pEnvData->pView ); |
519 |
#elif defined UNX |
520 |
// need a new PluginComm |
521 |
PluginComm* pComm = NULL; |
522 |
int sv[2]; |
523 |
if( !socketpair( AF_UNIX, SOCK_STREAM, 0, sv ) ) |
524 |
pComm = new UnxPluginComm( m_aDescription.Mimetype, |
525 |
m_aDescription.PluginName, |
526 |
(XLIB_Window)pEnvData->aWindow, |
527 |
sv[0], |
528 |
sv[1] |
529 |
); |
530 |
#elif (defined WNT || defined OS2) |
531 |
PluginComm* pComm = new PluginComm_Impl( m_aDescription.Mimetype, |
532 |
m_aDescription.PluginName, |
533 |
(HWND)pEnvData->hWnd ); |
534 |
#endif |
535 |
setPluginComm( pComm ); |
536 |
} |
537 |
else |
538 |
return; |
539 |
} |
540 |
|
541 |
NPError aError = getPluginComm()-> |
542 |
NPP_New( (char*)OUStringToOString( m_aDescription.Mimetype, |
543 |
m_aEncoding).getStr(), |
544 |
getNPPInstance(), |
545 |
m_aPluginMode == PluginMode::FULL ? NP_FULL : NP_EMBED, |
546 |
::sal::static_int_cast< int16, int >( m_nArgs ), |
547 |
(char**)(m_nArgs ? m_pArgn : NULL), |
548 |
(char**)(m_nArgs ? m_pArgv : NULL), |
549 |
NULL ); |
550 |
#ifdef QUARTZ |
551 |
// m_aNPWindow is set up in the MacPluginComm from the view |
552 |
m_aSysPlugData.m_pParentView = pEnvData->pView; |
553 |
#elif defined( UNX ) |
554 |
XSync( (Display*)pEnvData->pDisplay, False ); |
555 |
m_aNPWindow.window = (void*)pEnvData->aWindow; |
556 |
m_aNPWindow.ws_info = NULL; |
557 |
#else |
558 |
m_aNPWindow.window = (void*)pEnvData->hWnd; |
559 |
#endif |
560 |
com::sun::star::awt::Rectangle aPosSize = getPosSize(); |
561 |
|
562 |
for( int i = 0; i < m_nArgs; i++ ) |
563 |
{ |
564 |
OString aName( m_pArgn[i] ); |
565 |
if( aName.equalsIgnoreAsciiCase( "width" ) ) |
566 |
{ |
567 |
OString aValue( m_pArgv[i] ); |
568 |
aPosSize.Width = aValue.toInt32(); |
569 |
} |
570 |
else if( aName.equalsIgnoreAsciiCase( "height" ) ) |
571 |
{ |
572 |
OString aValue( m_pArgv[i] ); |
573 |
aPosSize.Height = aValue.toInt32(); |
574 |
} |
575 |
} |
576 |
|
577 |
m_aNPWindow.clipRect.top = 0; |
578 |
m_aNPWindow.clipRect.left = 0; |
579 |
m_aNPWindow.clipRect.bottom = ::sal::static_int_cast< uint16, sal_Int32 >( aPosSize.Height ); |
580 |
m_aNPWindow.clipRect.right = ::sal::static_int_cast< uint16, sal_Int32 >( aPosSize.Width ); |
581 |
m_aNPWindow.type = NPWindowTypeWindow; |
582 |
|
583 |
m_aNPWindow.x = 0; |
584 |
m_aNPWindow.y = 0; |
585 |
m_aNPWindow.width = aPosSize.Width ? aPosSize.Width : 600; |
586 |
m_aNPWindow.height = aPosSize.Height ? aPosSize.Height : 600; |
587 |
|
588 |
aError = getPluginComm()->NPP_SetWindow( this ); |
589 |
(void) aError; |
590 |
} |
591 |
|
592 |
void XPlugin_Impl::destroyStreams() |
593 |
{ |
594 |
Guard< Mutex > aGuard( m_aMutex ); |
595 |
|
596 |
// streams remove themselves from this list when deleted |
597 |
while( m_aOutputStreams.size() ) |
598 |
delete *m_aOutputStreams.begin(); |
599 |
|
600 |
// input streams are XOutputStreams, they cannot be simply deleted |
601 |
std::list<PluginInputStream*> aLocalList( m_aInputStreams ); |
602 |
for( std::list<PluginInputStream*>::iterator it = aLocalList.begin(); |
603 |
it != aLocalList.end(); ++it ) |
604 |
(*it)->setMode( -1 ); |
605 |
} |
606 |
|
607 |
PluginStream* XPlugin_Impl::getStreamFromNPStream( NPStream* stream ) |
608 |
{ |
609 |
Guard< Mutex > aGuard( m_aMutex ); |
610 |
|
611 |
std::list<PluginInputStream*>::iterator iter; |
612 |
for( iter = m_aInputStreams.begin(); iter != m_aInputStreams.end(); ++iter ) |
613 |
if( (*iter)->getStream() == stream ) |
614 |
return *iter; |
615 |
|
616 |
std::list<PluginOutputStream*>::iterator iter2; |
617 |
for( iter2 = m_aOutputStreams.begin(); iter2 != m_aOutputStreams.end(); ++iter2 ) |
618 |
if( (*iter2)->getStream() == stream ) |
619 |
return *iter2; |
620 |
|
621 |
return NULL; |
622 |
} |
623 |
|
624 |
sal_Bool XPlugin_Impl::provideNewStream(const OUString& mimetype, |
625 |
const uno::Reference< com::sun::star::io::XActiveDataSource > & stream, |
626 |
const OUString& url, sal_Int32 length, |
627 |
sal_Int32 lastmodified, sal_Bool isfile) throw() |
628 |
|
629 |
{ |
630 |
Guard< Mutex > aGuard( m_aMutex ); |
631 |
sal_Bool bRet = sal_False; |
632 |
|
633 |
if( m_nProvidingState != PROVIDING_NONE ) |
634 |
{ |
635 |
m_nProvidingState = PROVIDING_NOW; |
636 |
Any aAny; |
637 |
aAny <<= url; |
638 |
uno::Reference< com::sun::star::beans::XPropertySet > xPS( m_xModel, UNO_QUERY ); |
639 |
if( xPS.is() ) |
640 |
{ |
641 |
try |
642 |
{ |
643 |
xPS->setPropertyValue( OUString::createFromAscii( "URL" ), aAny ); |
644 |
aAny <<= mimetype; |
645 |
xPS->setPropertyValue( OUString::createFromAscii( "TYPE" ), aAny ); |
646 |
} |
647 |
catch(...) |
648 |
{ |
649 |
} |
650 |
} |
651 |
} |
652 |
m_nProvidingState = PROVIDING_NOW; |
653 |
|
654 |
OString aMIME; |
655 |
if( mimetype.getLength() ) |
656 |
aMIME = OUStringToOString( mimetype, m_aEncoding ); |
657 |
else |
658 |
aMIME = OUStringToOString( m_aDescription.Mimetype, m_aEncoding ); |
659 |
|
660 |
OString aURL = OUStringToOString( url, m_aEncoding ); |
661 |
|
662 |
// check wether there is a notifylistener for this stream |
663 |
// this means that the strema is created from the plugin |
664 |
// via NPN_GetURLNotify or NPN_PostURLNotify |
665 |
std::list<PluginEventListener*>::iterator iter; |
666 |
for( iter = m_aPEventListeners.begin(); |
667 |
iter != m_aPEventListeners.end(); |
668 |
++iter ) |
669 |
{ |
670 |
if( (*iter)->getNormalizedURL() == aURL ) |
671 |
{ |
672 |
aURL = (*iter)->getURL(); |
673 |
break; |
674 |
} |
675 |
} |
676 |
|
677 |
if( ! m_pPluginComm ) |
678 |
{ |
679 |
loadPlugin(); |
680 |
if( m_aLastGetUrl.getLength() && m_aLastGetUrl == aURL ) |
681 |
{ |
682 |
// plugin is pulling data, don't push the same stream; |
683 |
// this complicated method could have been avoided if |
684 |
// all plugins respected the SRC parameter; but e.g. |
685 |
// acrobat reader plugin does not |
686 |
m_nProvidingState = PROVIDING_NONE; |
687 |
return sal_True; |
688 |
} |
689 |
} |
690 |
if( ! m_pPluginComm ) |
691 |
return sal_False; |
692 |
|
693 |
if( ! url.getLength() ) |
694 |
// this is valid if the plugin is supposed to |
695 |
// pull data (via e.g. NPN_GetURL) |
696 |
return sal_True; |
697 |
|
698 |
// set mimetype on model |
699 |
{ |
700 |
uno::Reference< com::sun::star::beans::XPropertySet > xPS( m_xModel, UNO_QUERY ); |
701 |
if( xPS.is() ) |
702 |
{ |
703 |
try |
704 |
{ |
705 |
Any aAny; |
706 |
aAny <<= m_aDescription.Mimetype; |
707 |
xPS->setPropertyValue( OUString::createFromAscii( "TYPE" ), aAny ); |
708 |
} |
709 |
catch(...) |
710 |
{ |
711 |
} |
712 |
} |
713 |
} |
714 |
|
715 |
// there may be plugins that can use the file length information, |
716 |
// but currently none are known. Since this file opening/seeking/closing |
717 |
// is rather costly, it is #if'ed out. If there are plugins known to |
718 |
// make use of the file length, simply put it in |
719 |
#if 0 |
720 |
if( isfile && ! length ) |
721 |
{ |
722 |
osl::File aFile( url ); |
723 |
if( aFile.open( OpenFlag_Read ) == FileBase::E_None ) |
724 |
{ |
725 |
aFile.setPos( Pos_End, 0 ); |
726 |
sal_uInt64 nPos = 0; |
727 |
if( aFile.getPos( nPos ) == FileBase::E_None ) |
728 |
length = nPos; |
729 |
aFile.close(); |
730 |
} |
731 |
} |
732 |
#endif |
733 |
|
734 |
PluginInputStream* pStream = new PluginInputStream( this, aURL.getStr(), |
735 |
length, lastmodified ); |
736 |
uno::Reference< com::sun::star::io::XOutputStream > xNewStream( pStream ); |
737 |
|
738 |
if( iter != m_aPEventListeners.end() ) |
739 |
pStream->getStream()->notifyData = (*iter)->getNotifyData(); |
740 |
|
741 |
uint16 stype = 0; |
742 |
|
743 |
// special handling acrobat reader |
744 |
// presenting a seekable stream to it does not seem to work correctly |
745 |
if( aMIME.equals( "application/pdf" ) ) |
746 |
isfile = sal_False; |
747 |
|
748 |
#if OSL_DEBUG_LEVEL > 1 |
749 |
fprintf( stderr, |
750 |
"new stream \"%s\" of MIMEType \"%s\"\n" |
751 |
"for plugin \"%s\"\n" |
752 |
"seekable = %s, length = %"SAL_PRIdINT32"\n", |
753 |
aURL.getStr(), aMIME.getStr(), getPluginComm()->getLibName().getStr(), |
754 |
isfile ? "true" : "false", length ); |
755 |
|
756 |
#endif |
757 |
if( ! m_pPluginComm->NPP_NewStream( &m_aInstance, |
758 |
(char*)aMIME.getStr(), |
759 |
pStream->getStream(), isfile, |
760 |
&stype ) ) |
761 |
{ |
762 |
#if OSL_DEBUG_LEVEL > 1 |
763 |
const char* pType; |
764 |
switch( stype ) |
765 |
{ |
766 |
case NP_NORMAL: pType = "NP_NORMAL";break; |
767 |
case NP_SEEK: pType = "NP_SEEK";break; |
768 |
case NP_ASFILE: pType = "NP_ASFILE";break; |
769 |
case NP_ASFILEONLY: pType = "NP_ASFILEONLY";break; |
770 |
default: pType = "unknown!!!"; |
771 |
} |
772 |
fprintf( stderr, "Plugin wants it in Mode %s\n", pType ); |
773 |
#endif |
774 |
if( isfile && stype == NP_ASFILEONLY ) |
775 |
{ |
776 |
OString aFileName; |
777 |
if( url.compareToAscii( "file:", 5 ) == 0 ) |
778 |
{ |
779 |
OUString aSysName; |
780 |
osl_getSystemPathFromFileURL( url.pData, &aSysName.pData ); |
781 |
aFileName = OUStringToOString( aSysName, m_aEncoding ); |
782 |
} |
783 |
else |
784 |
aFileName = OUStringToOString( url, m_aEncoding ); |
785 |
m_pPluginComm-> |
786 |
NPP_StreamAsFile( &m_aInstance, |
787 |
pStream->getStream(), |
788 |
aFileName.getStr() ); |
789 |
} |
790 |
else |
791 |
{ |
792 |
pStream->setMode( stype ); |
793 |
|
794 |
if( ! stream.is() ) |
795 |
{ |
796 |
// stream has to be loaded by PluginStream itself via UCB |
797 |
pStream->load(); |
798 |
} |
799 |
else |
800 |
{ |
801 |
uno::Reference< com::sun::star::io::XConnectable > xConnectable( stream, UNO_QUERY ); |
802 |
pStream->setPredecessor( xConnectable ); |
803 |
if( xConnectable.is() ) |
804 |
{ |
805 |
xConnectable->setSuccessor( static_cast< com::sun::star::io::XConnectable* >(pStream) ); |
806 |
while( xConnectable->getPredecessor().is() ) |
807 |
xConnectable = xConnectable->getPredecessor(); |
808 |
} |
809 |
stream->setOutputStream( xNewStream ); |
810 |
pStream->setSource( stream ); |
811 |
uno::Reference< com::sun::star::io::XActiveDataControl > xController; |
812 |
if( xConnectable.is() ) |
813 |
xController = uno::Reference< com::sun::star::io::XActiveDataControl >( xConnectable, UNO_QUERY ); |
814 |
else |
815 |
xController = uno::Reference< com::sun::star::io::XActiveDataControl >( stream, UNO_QUERY ); |
816 |
|
817 |
if( xController.is() ) |
818 |
xController->start(); |
819 |
} |
820 |
} |
821 |
bRet = sal_True; |
822 |
} |
823 |
|
824 |
m_nProvidingState = PROVIDING_NONE; |
825 |
|
826 |
return bRet; |
827 |
} |
828 |
|
829 |
void XPlugin_Impl::disposing( const com::sun::star::lang::EventObject& /*rSource*/ ) throw() |
830 |
{ |
831 |
} |
832 |
|
833 |
void XPlugin_Impl::propertyChange( const com::sun::star::beans::PropertyChangeEvent& rEvent ) throw() |
834 |
{ |
835 |
Guard< Mutex > aGuard( m_aMutex ); |
836 |
|
837 |
if( ! rEvent.PropertyName.compareToAscii( "URL" ) ) |
838 |
{ |
839 |
OUString aStr; |
840 |
rEvent.NewValue >>= aStr; |
841 |
if( m_nProvidingState == PROVIDING_NONE ) |
842 |
{ |
843 |
if( aStr != m_aURL ) |
844 |
{ |
845 |
m_aURL = aStr; |
846 |
modelChanged(); |
847 |
} |
848 |
} |
849 |
} |
850 |
} |
851 |
|
852 |
void XPlugin_Impl::setPluginContext( const uno::Reference< XPluginContext > & rContext ) |
853 |
{ |
854 |
m_rBrowserContext = rContext; |
855 |
} |
856 |
|
857 |
void XPlugin_Impl::setPosSize( sal_Int32 nX_, sal_Int32 nY_, sal_Int32 nWidth_, sal_Int32 nHeight_, sal_Int16 nFlags ) |
858 |
throw( RuntimeException ) |
859 |
{ |
860 |
Guard< Mutex > aGuard( m_aMutex ); |
861 |
|
862 |
#if OSL_DEBUG_LEVEL > 1 |
863 |
fprintf( stderr, "XPlugin_Impl::setPosSize( %"SAL_PRIdINT32", %"SAL_PRIdINT32", %"SAL_PRIdINT32", %"SAL_PRIdINT32", %d )\n", |
864 |
nX_, nY_, nWidth_, nHeight_, nFlags ); |
865 |
#endif |
866 |
|
867 |
PluginControl_Impl::setPosSize(nX_, nY_, nWidth_, nHeight_, nFlags); |
868 |
|
869 |
m_aNPWindow.x = 0; |
870 |
m_aNPWindow.y = 0; |
871 |
m_aNPWindow.width = nWidth_; |
872 |
m_aNPWindow.height = nHeight_; |
873 |
m_aNPWindow.clipRect.top = 0; |
874 |
m_aNPWindow.clipRect.left = 0; |
875 |
m_aNPWindow.clipRect.right = ::sal::static_int_cast< uint16, sal_Int32 >( nWidth_ ); |
876 |
m_aNPWindow.clipRect.bottom = ::sal::static_int_cast< uint16, sal_Int32 >( nHeight_ ); |
877 |
|
878 |
if( getPluginComm() ) |
879 |
getPluginComm()->NPP_SetWindow( this ); |
880 |
} |
881 |
|
882 |
PluginDescription XPlugin_Impl::fitDescription( const OUString& rURL ) |
883 |
{ |
884 |
uno::Reference< XPluginManager > xPMgr( |
885 |
m_xContext->getServiceManager()->createInstanceWithContext( |
886 |
OUString( RTL_CONSTASCII_USTRINGPARAM( |
887 |
"com.sun.star.plugin.PluginManager" )), m_xContext ), UNO_QUERY ); |
888 |
if( !xPMgr.is() ) |
889 |
{ |
890 |
m_nProvidingState = PROVIDING_NONE; |
891 |
return PluginDescription(); |
892 |
} |
893 |
|
894 |
Sequence< PluginDescription > aDescrs = xPMgr->getPluginDescriptions(); |
895 |
const PluginDescription* pDescrs = aDescrs.getConstArray(); |
896 |
|
897 |
for( int nArg = 0; nArg < m_nArgs; nArg++ ) |
898 |
{ |
899 |
if( strncmp( m_pArgn[nArg], "TYPE", 4 ) == 0 && |
900 |
m_pArgn[nArg][4] == 0 ) |
901 |
{ |
902 |
for( int i = 0; i < aDescrs.getLength(); i++ ) |
903 |
{ |
904 |
if( pDescrs[i].Mimetype.compareToAscii( m_pArgv[nArg] ) == 0 ) |
905 |
return pDescrs[i]; |
906 |
} |
907 |
} |
908 |
} |
909 |
|
910 |
int nPos = rURL.lastIndexOf( (sal_Unicode)'.' ); |
911 |
OUString aExt = rURL.copy( nPos ).toAsciiLowerCase(); |
912 |
if( nPos != -1 ) |
913 |
{ |
914 |
for( int i = 0; i < aDescrs.getLength(); i++ ) |
915 |
{ |
916 |
OUString aThisExt = pDescrs[ i ].Extension.toAsciiLowerCase(); |
917 |
if( aThisExt.indexOf( aExt ) != -1 ) |
918 |
{ |
919 |
return pDescrs[i]; |
920 |
} |
921 |
} |
922 |
} |
923 |
return PluginDescription(); |
924 |
} |
925 |
|
926 |
|
927 |
PluginStream::PluginStream( XPlugin_Impl* pPlugin, |
928 |
const char* url, sal_uInt32 len, sal_uInt32 lastmod ) : |
929 |
m_pPlugin( pPlugin ) |
930 |
{ |
931 |
memset( &m_aNPStream, 0, sizeof( m_aNPStream ) ); |
932 |
m_aNPStream.url = strdup( url ); |
933 |
m_aNPStream.end = len; |
934 |
m_aNPStream.lastmodified = lastmod; |
935 |
} |
936 |
|
937 |
PluginStream::~PluginStream() |
938 |
{ |
939 |
Guard< Mutex > aGuard( m_pPlugin->getMutex() ); |
940 |
|
941 |
if( m_pPlugin && m_pPlugin->getPluginComm() ) |
942 |
{ |
943 |
m_pPlugin->getPluginComm()->NPP_DestroyStream( m_pPlugin->getNPPInstance(), |
944 |
&m_aNPStream, NPRES_DONE ); |
945 |
m_pPlugin->checkListeners( m_aNPStream.url ); |
946 |
m_pPlugin->getPluginComm()->NPP_SetWindow( m_pPlugin ); |
947 |
} |
948 |
::free( (void*)m_aNPStream.url ); |
949 |
} |
950 |
|
951 |
PluginInputStream::PluginInputStream( XPlugin_Impl* pPlugin, |
952 |
const char* url, |
953 |
sal_uInt32 len, |
954 |
sal_uInt32 lastmod ) : |
955 |
PluginStream( pPlugin, url, len, lastmod ), |
956 |
m_pContent( NULL ), |
957 |
m_nMode( NP_NORMAL ), |
958 |
m_nWritePos( 0 ) |
959 |
{ |
960 |
Guard< Mutex > aGuard( m_pPlugin->getMutex() ); |
961 |
|
962 |
m_pPlugin->getInputStreams().push_back( this ); |
963 |
DirEntry aEntry; |
964 |
aEntry = aEntry.TempName(); |
965 |
|
966 |
// set correct extension, some plugins need that |
967 |
DirEntry aName( String( m_aNPStream.url, m_pPlugin->getTextEncoding() ) ); |
968 |
String aExtension = aName.GetExtension(); |
969 |
if( aExtension.Len() ) |
970 |
aEntry.SetExtension( aExtension ); |
971 |
m_aFileStream.Open( aEntry.GetFull(), STREAM_READ | STREAM_WRITE ); |
972 |
if( ! m_aFileStream.IsOpen() ) |
973 |
{ |
974 |
// #74808# might be that the extension scrambled the whole filename |
975 |
aEntry = aEntry.TempName(); |
976 |
m_aFileStream.Open( aEntry.GetFull(), STREAM_READ | STREAM_WRITE ); |
977 |
} |
978 |
} |
979 |
|
980 |
PluginInputStream::~PluginInputStream() |
981 |
{ |
982 |
Guard< Mutex > aGuard( m_pPlugin->getMutex() ); |
983 |
|
984 |
m_pPlugin->getInputStreams().remove( this ); |
985 |
|
986 |
String aFile( m_aFileStream.GetFileName() ); |
987 |
|
988 |
m_aFileStream.Close(); |
989 |
if( m_pPlugin ) |
990 |
{ |
991 |
ByteString aFileName( aFile, m_pPlugin->getTextEncoding() ); |
992 |
if( m_pPlugin->getPluginComm() && m_nMode != -1 ) |
993 |
// mode -1 means either an error occured, |
994 |
// or the plugin is already disposing |
995 |
{ |
996 |
m_pPlugin->getPluginComm()->addFileToDelete( aFile ); |
997 |
if( m_nMode == NP_ASFILE ) |
998 |
{ |
999 |
m_pPlugin->getPluginComm()-> |
1000 |
NPP_StreamAsFile( m_pPlugin->getNPPInstance(), |
1001 |
&m_aNPStream, |
1002 |
aFileName.GetBuffer() ); |
1003 |
} |
1004 |
m_pPlugin->getPluginComm()->NPP_SetWindow( m_pPlugin ); |
1005 |
m_pPlugin->getInputStreams().remove( this ); |
1006 |
} |
1007 |
else |
1008 |
DirEntry( m_aFileStream.GetFileName() ).Kill(); |
1009 |
} |
1010 |
else |
1011 |
DirEntry( m_aFileStream.GetFileName() ).Kill(); |
1012 |
if( m_pContent ) |
1013 |
delete m_pContent; |
1014 |
} |
1015 |
|
1016 |
PluginStreamType PluginInputStream::getStreamType() |
1017 |
{ |
1018 |
return InputStream; |
1019 |
} |
1020 |
|
1021 |
void PluginInputStream::load() |
1022 |
{ |
1023 |
Guard< Mutex > aGuard( m_pPlugin->getMutex() ); |
1024 |
|
1025 |
INetURLObject aUrl; |
1026 |
aUrl.SetSmartProtocol( INET_PROT_FILE ); |
1027 |
aUrl.SetSmartURL( |
1028 |
String( getStream()->url, |
1029 |
::sal::static_int_cast< sal_uInt16, size_t >( strlen( getStream()->url ) ), |
1030 |
RTL_TEXTENCODING_MS_1252 |
1031 |
) ); |
1032 |
try |
1033 |
{ |
1034 |
m_pContent = |
1035 |
new ::ucbhelper::Content( |
1036 |
aUrl.GetMainURL(INetURLObject::DECODE_TO_IURI), |
1037 |
uno::Reference< com::sun::star::ucb::XCommandEnvironment >() |
1038 |
); |
1039 |
m_pContent->openStream( static_cast< XOutputStream* >( this ) ); |
1040 |
} |
1041 |
catch( com::sun::star::uno::Exception ) |
1042 |
{ |
1043 |
} |
1044 |
} |
1045 |
|
1046 |
void PluginInputStream::setMode( sal_Int32 nMode ) |
1047 |
{ |
1048 |
Guard< Mutex > aGuard( m_pPlugin->getMutex() ); |
1049 |
|
1050 |
m_nMode = nMode; |
1051 |
|
1052 |
// invalidation by plugin |
1053 |
if( m_nMode == -1 && m_pPlugin ) |
1054 |
{ |
1055 |
m_pPlugin->getInputStreams().remove( this ); |
1056 |
m_pPlugin = NULL; |
1057 |
} |
1058 |
} |
1059 |
|
1060 |
void PluginInputStream::writeBytes( const Sequence<sal_Int8>& Buffer ) throw() |
1061 |
{ |
1062 |
Guard< Mutex > aGuard( m_pPlugin->getMutex() ); |
1063 |
|
1064 |
m_aFileStream.Seek( STREAM_SEEK_TO_END ); |
1065 |
m_aFileStream.Write( Buffer.getConstArray(), Buffer.getLength() ); |
1066 |
|
1067 |
if( m_nMode == NP_SEEK ) |
1068 |
// hold reference, streem gets destroyed in NPN_DestroyStream |
1069 |
m_xSelf = this; |
1070 |
|
1071 |
if( m_nMode == -1 || !m_pPlugin->getPluginComm() ) |
1072 |
return; |
1073 |
|
1074 |
sal_uInt32 nPos = m_aFileStream.Tell(); |
1075 |
sal_uInt32 nBytes = 0; |
1076 |
while( m_nMode != NP_ASFILEONLY && |
1077 |
m_nWritePos < nPos && |
1078 |
(nBytes = m_pPlugin->getPluginComm()-> NPP_WriteReady( |
1079 |
m_pPlugin->getNPPInstance(), &m_aNPStream )) > 0 ) |
1080 |
{ |
1081 |
nBytes = (nBytes > nPos - m_nWritePos) ? nPos - m_nWritePos : nBytes; |
1082 |
|
1083 |
char* pBuffer = new char[ nBytes ]; |
1084 |
m_aFileStream.Seek( m_nWritePos ); |
1085 |
nBytes = m_aFileStream.Read( pBuffer, nBytes ); |
1086 |
|
1087 |
int32 nBytesRead = 0; |
1088 |
try |
1089 |
{ |
1090 |
nBytesRead = m_pPlugin->getPluginComm()->NPP_Write( |
1091 |
m_pPlugin->getNPPInstance(), &m_aNPStream, m_nWritePos, nBytes, pBuffer ); |
1092 |
} |
1093 |
catch( ... ) |
1094 |
{ |
1095 |
nBytesRead = 0; |
1096 |
} |
1097 |
delete [] pBuffer; |
1098 |
|
1099 |
if( nBytesRead < 0 ) |
1100 |
{ |
1101 |
m_nMode = -1; |
1102 |
return; |
1103 |
} |
1104 |
|
1105 |
m_nWritePos += nBytesRead; |
1106 |
} |
1107 |
} |
1108 |
|
1109 |
void PluginInputStream::closeOutput() throw() |
1110 |
{ |
1111 |
Guard< Mutex > aGuard( m_pPlugin->getMutex() ); |
1112 |
|
1113 |
flush(); |
1114 |
m_xSource = uno::Reference< com::sun::star::io::XActiveDataSource >(); |
1115 |
} |
1116 |
|
1117 |
sal_uInt32 PluginInputStream::read( sal_uInt32 offset, sal_Int8* buffer, sal_uInt32 size ) |
1118 |
{ |
1119 |
Guard< Mutex > aGuard( m_pPlugin->getMutex() ); |
1120 |
|
1121 |
if( m_nMode != NP_SEEK ) |
1122 |
return 0; |
1123 |
|
1124 |
m_aFileStream.Seek( offset ); |
1125 |
return m_aFileStream.Read( buffer, size ); |
1126 |
} |
1127 |
|
1128 |
void PluginInputStream::flush(void) throw() |
1129 |
{ |
1130 |
} |
1131 |
|
1132 |
PluginOutputStream::PluginOutputStream( XPlugin_Impl* pPlugin, |
1133 |
const char* url, |
1134 |
sal_uInt32 len, |
1135 |
sal_uInt32 lastmod ) : |
1136 |
PluginStream( pPlugin, url, len, lastmod ), |
1137 |
m_xStream( pPlugin->getComponentContext() |
1138 |
->getServiceManager()->createInstanceWithContext( |
1139 |
OUString( RTL_CONSTASCII_USTRINGPARAM( |
1140 |
"com.sun.star.io.DataOutputStream" )), |
1141 |
pPlugin->getComponentContext() ), UNO_QUERY ) |
1142 |
{ |
1143 |
Guard< Mutex > aGuard( m_pPlugin->getMutex() ); |
1144 |
|
1145 |
m_pPlugin->getOutputStreams().push_back( this ); |
1146 |
} |
1147 |
|
1148 |
PluginOutputStream::~PluginOutputStream() |
1149 |
{ |
1150 |
Guard< Mutex > aGuard( m_pPlugin->getMutex() ); |
1151 |
|
1152 |
m_pPlugin->getOutputStreams().remove( this ); |
1153 |
} |
1154 |
|
1155 |
PluginStreamType PluginOutputStream::getStreamType() |
1156 |
{ |
1157 |
return OutputStream; |
1158 |
} |
1159 |
|