Branch data Line data Source code
1 : : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : : /*
3 : : * This file is part of the LibreOffice project.
4 : : *
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/.
8 : : *
9 : : * This file incorporates work covered by the following license notice:
10 : : *
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 .
18 : : */
19 : :
20 : :
21 : : #include "passwordcontainer.hxx"
22 : :
23 : : #include <unotools/pathoptions.hxx>
24 : : #include <cppuhelper/factory.hxx>
25 : : #include <comphelper/string.hxx>
26 : : #include <com/sun/star/registry/XSimpleRegistry.hpp>
27 : : #include <com/sun/star/beans/PropertyValue.hpp>
28 : : #include <com/sun/star/task/MasterPasswordRequest.hpp>
29 : : #include <com/sun/star/task/NoMasterException.hpp>
30 : :
31 : : #include <rtl/cipher.h>
32 : : #include <rtl/digest.h>
33 : : #include <rtl/byteseq.hxx>
34 : :
35 : : using namespace std;
36 : : using namespace osl;
37 : : using namespace utl;
38 : : using namespace com::sun::star;
39 : : using namespace com::sun::star::uno;
40 : : using namespace com::sun::star::registry;
41 : : using namespace com::sun::star::lang;
42 : : using namespace com::sun::star::task;
43 : : using namespace com::sun::star::ucb;
44 : :
45 : : //-------------------------------------------------------------------------
46 : : //-------------------------------------------------------------------------
47 : :
48 : 154 : static ::rtl::OUString createIndex( vector< ::rtl::OUString > lines )
49 : : {
50 : 154 : ::rtl::OString aResult;
51 : : const sal_Char* pLine;
52 : :
53 [ + + ]: 408 : for( unsigned int i = 0; i < lines.size(); i++ )
54 : : {
55 [ + + ]: 254 : if( i )
56 : 100 : aResult += ::rtl::OString( "__" );
57 [ + - ]: 254 : ::rtl::OString line = ::rtl::OUStringToOString( lines[i], RTL_TEXTENCODING_UTF8 );
58 : 254 : pLine = line.getStr();
59 : :
60 [ + + ]: 4582 : while( *pLine )
61 : : {
62 [ + - ][ + + ]: 4328 : if (comphelper::string::isalnumAscii(*pLine))
63 : : {
64 : 3528 : aResult += ::rtl::OString::valueOf( *pLine );
65 : : }
66 : : else
67 : : {
68 : 800 : aResult += ::rtl::OString("_");
69 : 800 : aResult += ::rtl::OString::valueOf( (sal_Int32) *pLine, 16 );
70 : : }
71 : :
72 : 4328 : pLine++;
73 : : }
74 : 254 : }
75 : :
76 : 154 : return ::rtl::OUString::createFromAscii( aResult.getStr() );
77 : : }
78 : :
79 : : //-------------------------------------------------------------------------
80 : :
81 : 40 : static vector< ::rtl::OUString > getInfoFromInd( ::rtl::OUString aInd )
82 : : {
83 [ + - ]: 40 : vector< ::rtl::OUString > aResult;
84 : 40 : sal_Bool aStart = sal_True;
85 : :
86 [ + - ]: 40 : ::rtl::OString line = ::rtl::OUStringToOString( aInd, RTL_TEXTENCODING_ASCII_US );
87 : 40 : const sal_Char* pLine = line.getStr();
88 [ - + ][ # # ]: 40 : do
[ - + ]
89 : : {
90 : 40 : ::rtl::OUString newItem;
91 [ - + ]: 40 : if( !aStart )
92 : 0 : pLine += 2;
93 : : else
94 : 40 : aStart = sal_False;
95 : :
96 [ + + ][ + + ]: 520 : while( *pLine && !( pLine[0] == '_' && pLine[1] == '_' ))
[ + - ][ + + ]
97 [ + + ]: 480 : if( *pLine != '_' )
98 : : {
99 : 400 : newItem += ::rtl::OUString::valueOf( (sal_Unicode) *pLine );
100 : 400 : pLine++;
101 : : }
102 : : else
103 : : {
104 : 80 : ::rtl::OUString aNum;
105 [ + + ]: 240 : for( int i = 1; i < 3; i++ )
106 : : {
107 [ + - ][ + - ]: 160 : if( !pLine[i]
[ + + ][ + - ]
[ - + ][ # # ]
[ # # ]
108 : 320 : || ( ( pLine[i] < '0' || pLine[i] > '9' )
109 : 160 : && ( pLine[i] < 'a' || pLine[i] > 'f' )
110 : 0 : && ( pLine[i] < 'A' || pLine[i] > 'F' ) ) )
111 : : {
112 : : OSL_FAIL( "Wrong index syntax!\n" );
113 : : return aResult;
114 : : }
115 : :
116 : 160 : aNum += ::rtl::OUString::valueOf( (sal_Unicode) pLine[i] );
117 : : }
118 : :
119 : 80 : newItem += ::rtl::OUString::valueOf( (sal_Unicode) aNum.toInt32( 16 ) );
120 [ + - ]: 80 : pLine += 3;
121 : : }
122 : :
123 [ + - ][ + - ]: 40 : aResult.push_back( newItem );
124 : 0 : } while( pLine[0] == '_' && pLine[1] == '_' );
125 : :
126 : 40 : if( *pLine )
127 : : OSL_FAIL( "Wrong index syntax!\n" );
128 : :
129 : 40 : return aResult;
130 : : }
131 : :
132 : : //-------------------------------------------------------------------------
133 : :
134 : 0 : static sal_Bool shorterUrl( ::rtl::OUString& aURL )
135 : : {
136 : 0 : sal_Int32 aInd = aURL.lastIndexOf( sal_Unicode( '/' ) );
137 [ # # ][ # # ]: 0 : if( aInd > 0 && aURL.indexOf( "://" ) != aInd-2 )
[ # # ]
138 : : {
139 : 0 : aURL = aURL.copy( 0, aInd );
140 : 0 : return sal_True;
141 : : }
142 : :
143 : 0 : return sal_False;
144 : : }
145 : :
146 : : //-------------------------------------------------------------------------
147 : :
148 : 54 : static ::rtl::OUString getAsciiLine( const ::rtl::ByteSequence& buf )
149 : : {
150 : 54 : ::rtl::OUString aResult;
151 : :
152 [ + - ]: 54 : ::rtl::ByteSequence outbuf( buf.getLength()*2+1 );
153 : :
154 [ + + ]: 1036 : for( int ind = 0; ind < buf.getLength(); ind++ )
155 : : {
156 [ + - ]: 982 : outbuf[ind*2] = ( ((sal_uInt8)buf[ind]) >> 4 ) + 'a';
157 [ + - ]: 982 : outbuf[ind*2+1] = ( ((sal_uInt8)buf[ind]) & 0x0f ) + 'a';
158 : : }
159 [ + - ]: 54 : outbuf[buf.getLength()*2] = '\0';
160 : :
161 [ + - ]: 54 : aResult = ::rtl::OUString::createFromAscii( (sal_Char*)outbuf.getArray() );
162 : :
163 : 54 : return aResult;
164 : : }
165 : :
166 : : //-------------------------------------------------------------------------
167 : :
168 : 40 : static ::rtl::ByteSequence getBufFromAsciiLine( ::rtl::OUString line )
169 : : {
170 : : OSL_ENSURE( line.getLength() % 2 == 0, "Wrong syntax!\n" );
171 [ + - ]: 40 : ::rtl::OString tmpLine = ::rtl::OUStringToOString( line, RTL_TEXTENCODING_ASCII_US );
172 [ + - ]: 40 : ::rtl::ByteSequence aResult(line.getLength()/2);
173 : :
174 [ + + ]: 720 : for( int ind = 0; ind < tmpLine.getLength()/2; ind++ )
175 : : {
176 [ + - ]: 680 : aResult[ind] = ( (sal_uInt8)( tmpLine.getStr()[ind*2] - 'a' ) << 4 ) | (sal_uInt8)( tmpLine.getStr()[ind*2+1] - 'a' );
177 : : }
178 : :
179 : 40 : return aResult;
180 : : }
181 : :
182 : : //-------------------------------------------------------------------------
183 : :
184 : 80 : static Sequence< ::rtl::OUString > copyVectorToSequence( const vector< ::rtl::OUString >& original )
185 : : {
186 : 80 : Sequence< ::rtl::OUString > newOne ( original.size() );
187 [ + + ]: 160 : for( unsigned int i = 0; i < original.size() ; i++ )
188 [ + - ]: 80 : newOne[i] = original[i];
189 : :
190 : 80 : return newOne;
191 : : }
192 : :
193 : 90 : static vector< ::rtl::OUString > copySequenceToVector( const Sequence< ::rtl::OUString >& original )
194 : : {
195 : 90 : vector< ::rtl::OUString > newOne ( original.getLength() );
196 [ + + ]: 180 : for( int i = 0; i < original.getLength() ; i++ )
197 : 90 : newOne[i] = original[i];
198 : :
199 : 90 : return newOne;
200 : : }
201 : :
202 : : //-------------------------------------------------------------------------
203 : : //-------------------------------------------------------------------------
204 : :
205 : 0 : PassMap StorageItem::getInfo()
206 : : {
207 [ # # ]: 0 : PassMap aResult;
208 : :
209 [ # # ]: 0 : Sequence< ::rtl::OUString > aNodeNames = ConfigItem::GetNodeNames( ::rtl::OUString("Store") );
210 : 0 : sal_Int32 aNodeCount = aNodeNames.getLength();
211 [ # # ]: 0 : Sequence< ::rtl::OUString > aPropNames( aNodeCount );
212 : : sal_Int32 aNodeInd;
213 : :
214 [ # # ]: 0 : for( aNodeInd = 0; aNodeInd < aNodeCount; ++aNodeInd )
215 : : {
216 [ # # ]: 0 : aPropNames[aNodeInd] = ::rtl::OUString("Store/Passwordstorage['");
217 [ # # ][ # # ]: 0 : aPropNames[aNodeInd] += aNodeNames[aNodeInd];
218 [ # # ]: 0 : aPropNames[aNodeInd] += ::rtl::OUString("']/Password");
219 : : }
220 : :
221 [ # # ]: 0 : Sequence< Any > aPropertyValues = ConfigItem::GetProperties( aPropNames );
222 : :
223 [ # # ]: 0 : if( aPropertyValues.getLength() != aNodeNames.getLength() )
224 : : {
225 : : OSL_ENSURE( aPropertyValues.getLength() == aNodeNames.getLength(), "Problems during reading\n" );
226 : : return aResult;
227 : : }
228 : :
229 [ # # ]: 0 : for( aNodeInd = 0; aNodeInd < aNodeCount; ++aNodeInd )
230 : : {
231 [ # # ][ # # ]: 0 : vector< ::rtl::OUString > aUrlUsr = getInfoFromInd( aNodeNames[aNodeInd] );
232 : :
233 [ # # ]: 0 : if( aUrlUsr.size() == 2 )
234 : : {
235 : 0 : ::rtl::OUString aUrl = aUrlUsr[0];
236 : 0 : ::rtl::OUString aName = aUrlUsr[1];
237 : :
238 : 0 : ::rtl::OUString aEPasswd;
239 [ # # ]: 0 : aPropertyValues[aNodeInd] >>= aEPasswd;
240 : :
241 [ # # ]: 0 : PassMap::iterator aIter = aResult.find( aUrl );
242 [ # # ]: 0 : if( aIter != aResult.end() )
243 [ # # ][ # # ]: 0 : aIter->second.push_back( NamePassRecord( aName, aEPasswd ) );
244 : : else
245 : : {
246 [ # # ]: 0 : NamePassRecord aNewRecord( aName, aEPasswd );
247 [ # # ]: 0 : list< NamePassRecord > listToAdd( 1, aNewRecord );
248 : :
249 [ # # ][ # # ]: 0 : aResult.insert( PairUrlRecord( aUrl, listToAdd ) );
250 : 0 : }
251 : : }
252 : : else
253 : : OSL_FAIL( "Wrong index sintax!\n" );
254 : 0 : }
255 : :
256 [ # # ][ # # ]: 0 : return aResult;
[ # # ]
257 : : }
258 : :
259 : : //-------------------------------------------------------------------------
260 : :
261 : 8 : void StorageItem::setUseStorage( sal_Bool bUse )
262 : : {
263 [ + - ]: 8 : Sequence< ::rtl::OUString > sendNames(1);
264 [ + - ]: 8 : Sequence< uno::Any > sendVals(1);
265 : :
266 [ + - ]: 8 : sendNames[0] = ::rtl::OUString("UseStorage");
267 : :
268 [ + - ][ + - ]: 8 : sendVals[0] <<= bUse;
269 : :
270 [ + - ]: 8 : ConfigItem::SetModified();
271 [ + - ][ + - ]: 8 : ConfigItem::PutProperties( sendNames, sendVals );
[ + - ]
272 : 8 : }
273 : :
274 : : //-------------------------------------------------------------------------
275 : :
276 : 104 : sal_Bool StorageItem::useStorage()
277 : : {
278 [ + - ]: 104 : Sequence< ::rtl::OUString > aNodeNames( 1 );
279 [ + - ]: 104 : aNodeNames[0] = ::rtl::OUString("UseStorage");
280 : :
281 [ + - ]: 104 : Sequence< Any > aPropertyValues = ConfigItem::GetProperties( aNodeNames );
282 : :
283 [ - + ]: 104 : if( aPropertyValues.getLength() != aNodeNames.getLength() )
284 : : {
285 : : OSL_ENSURE( aPropertyValues.getLength() == aNodeNames.getLength(), "Problems during reading\n" );
286 : 0 : return sal_False;
287 : : }
288 : :
289 : 104 : sal_Bool aResult = false;
290 [ + - ]: 104 : aPropertyValues[0] >>= aResult;
291 : :
292 [ + - ][ + - ]: 104 : return aResult;
293 : : }
294 : :
295 : : //-------------------------------------------------------------------------
296 : :
297 : 4 : sal_Bool StorageItem::getEncodedMP( ::rtl::OUString& aResult )
298 : : {
299 [ - + ]: 4 : if( hasEncoded )
300 : : {
301 : 0 : aResult = mEncoded;
302 : 0 : return sal_True;
303 : : }
304 : :
305 [ + - ]: 4 : Sequence< ::rtl::OUString > aNodeNames( 2 );
306 [ + - ]: 4 : aNodeNames[0] = ::rtl::OUString("HasMaster");
307 [ + - ]: 4 : aNodeNames[1] = ::rtl::OUString("Master");
308 : :
309 [ + - ]: 4 : Sequence< Any > aPropertyValues = ConfigItem::GetProperties( aNodeNames );
310 : :
311 [ - + ]: 4 : if( aPropertyValues.getLength() != aNodeNames.getLength() )
312 : : {
313 : : OSL_ENSURE( aPropertyValues.getLength() == aNodeNames.getLength(), "Problems during reading\n" );
314 : 0 : return sal_False;
315 : : }
316 : :
317 [ + - ]: 4 : aPropertyValues[0] >>= hasEncoded;
318 [ + - ]: 4 : aPropertyValues[1] >>= mEncoded;
319 : :
320 : 4 : aResult = mEncoded;
321 : :
322 [ + - ][ + - ]: 4 : return hasEncoded;
323 : : }
324 : :
325 : : //-------------------------------------------------------------------------
326 : :
327 : 8 : void StorageItem::setEncodedMP( const ::rtl::OUString& aEncoded, sal_Bool bAcceptEmpty )
328 : : {
329 [ + - ]: 8 : Sequence< ::rtl::OUString > sendNames(2);
330 [ + - ]: 8 : Sequence< uno::Any > sendVals(2);
331 : :
332 [ + - ]: 8 : sendNames[0] = ::rtl::OUString("HasMaster");
333 [ + - ]: 8 : sendNames[1] = ::rtl::OUString("Master");
334 : :
335 [ - + ][ + + ]: 8 : sal_Bool bHasMaster = ( !aEncoded.isEmpty() || bAcceptEmpty );
336 [ + - ][ + - ]: 8 : sendVals[0] <<= bHasMaster;
337 [ + - ][ + - ]: 8 : sendVals[1] <<= aEncoded;
338 : :
339 [ + - ]: 8 : ConfigItem::SetModified();
340 [ + - ]: 8 : ConfigItem::PutProperties( sendNames, sendVals );
341 : :
342 : 8 : hasEncoded = bHasMaster;
343 [ + - ][ + - ]: 8 : mEncoded = aEncoded;
344 : 8 : }
345 : :
346 : : //-------------------------------------------------------------------------
347 : :
348 : 50 : void StorageItem::remove( const ::rtl::OUString& aURL, const ::rtl::OUString& aName )
349 : : {
350 [ + - ]: 50 : vector < ::rtl::OUString > forIndex;
351 [ + - ]: 50 : forIndex.push_back( aURL );
352 [ + - ]: 50 : forIndex.push_back( aName );
353 : :
354 [ + - ]: 50 : Sequence< ::rtl::OUString > sendSeq(1);
355 : :
356 [ + - ][ + - ]: 50 : sendSeq[0] = createIndex( forIndex );
[ + - ]
357 : :
358 [ + - ][ + - ]: 50 : ConfigItem::ClearNodeElements( ::rtl::OUString("Store"), sendSeq );
359 : 50 : }
360 : :
361 : : //-------------------------------------------------------------------------
362 : :
363 : 8 : void StorageItem::clear()
364 : : {
365 [ + - ]: 8 : Sequence< ::rtl::OUString > sendSeq(1);
366 : :
367 [ + - ][ + - ]: 8 : ConfigItem::ClearNodeSet( ::rtl::OUString("Store") );
368 : 8 : }
369 : :
370 : : //-------------------------------------------------------------------------
371 : :
372 : 50 : void StorageItem::update( const ::rtl::OUString& aURL, const NamePassRecord& aRecord )
373 : : {
374 [ + - ]: 50 : if ( !aRecord.HasPasswords( PERSISTENT_RECORD ) )
375 : : {
376 : : OSL_FAIL( "Unexpected storing of a record!" );
377 : 50 : return;
378 : : }
379 : :
380 [ + - ]: 50 : vector < ::rtl::OUString > forIndex;
381 [ + - ]: 50 : forIndex.push_back( aURL );
382 [ + - ]: 50 : forIndex.push_back( aRecord.GetUserName() );
383 : :
384 [ + - ]: 50 : Sequence< beans::PropertyValue > sendSeq(1);
385 : :
386 [ + - ]: 50 : sendSeq[0].Name = ::rtl::OUString("Store/Passwordstorage['");
387 [ + - ][ + - ]: 50 : sendSeq[0].Name += createIndex( forIndex );
[ + - ]
388 [ + - ]: 50 : sendSeq[0].Name += ::rtl::OUString("']/Password");
389 : :
390 [ + - ][ + - ]: 50 : sendSeq[0].Value <<= aRecord.GetPersPasswords();
391 : :
392 [ + - ]: 50 : ConfigItem::SetModified();
393 [ + - ][ + - ]: 50 : ConfigItem::SetSetProperties( ::rtl::OUString("Store"), sendSeq );
[ + - ][ + - ]
394 : : }
395 : :
396 : : //-------------------------------------------------------------------------
397 : :
398 : 0 : void StorageItem::Notify( const Sequence< ::rtl::OUString >& )
399 : : {
400 : : // this feature still should not be used
401 [ # # ]: 0 : if( mainCont )
402 : 0 : mainCont->Notify();
403 : 0 : }
404 : :
405 : : //-------------------------------------------------------------------------
406 : :
407 : 2 : void StorageItem::Commit()
408 : : {
409 : : // Do nothing, we stored everything we want already
410 : 2 : }
411 : :
412 : : //-------------------------------------------------------------------------
413 : : //-------------------------------------------------------------------------
414 : :
415 : 2 : PasswordContainer::PasswordContainer( const Reference<XMultiServiceFactory>& xServiceFactory ):
416 [ + - ][ + - ]: 2 : m_pStorageFile( NULL )
[ + - ]
417 : : {
418 : : // m_pStorageFile->Notify() can be called
419 [ + - ]: 2 : ::osl::MutexGuard aGuard( mMutex );
420 : :
421 [ + - ][ + - ]: 2 : mComponent = Reference< XComponent >( xServiceFactory, UNO_QUERY );
422 [ + - ][ + - ]: 2 : mComponent->addEventListener( this );
[ + - ]
423 : :
424 [ + - ][ + - ]: 2 : m_pStorageFile = new StorageItem( this, ::rtl::OUString("Office.Common/Passwords") );
425 [ + - ]: 2 : if( m_pStorageFile )
426 [ + - ][ - + ]: 2 : if( m_pStorageFile->useStorage() )
427 [ # # ][ # # ]: 2 : m_aContainer = m_pStorageFile->getInfo();
[ + - ]
428 : 2 : }
429 : :
430 : : //-------------------------------------------------------------------------
431 : :
432 [ + - ][ + - ]: 2 : PasswordContainer::~PasswordContainer()
433 : : {
434 [ + - ]: 2 : ::osl::MutexGuard aGuard( mMutex );
435 : :
436 [ - + ]: 2 : if( m_pStorageFile )
437 : : {
438 [ # # ][ # # ]: 0 : delete m_pStorageFile;
439 : 0 : m_pStorageFile = NULL;
440 : : }
441 : :
442 [ - + ]: 2 : if( mComponent.is() )
443 : : {
444 [ # # ][ # # ]: 0 : mComponent->removeEventListener(this);
[ # # ]
445 [ # # ]: 0 : mComponent = Reference< XComponent >();
446 [ + - ]: 2 : }
447 [ - + ]: 4 : }
448 : :
449 : : //-------------------------------------------------------------------------
450 : :
451 : 2 : void SAL_CALL PasswordContainer::disposing( const EventObject& ) throw(RuntimeException)
452 : : {
453 [ + - ]: 2 : ::osl::MutexGuard aGuard( mMutex );
454 : :
455 [ + - ]: 2 : if( m_pStorageFile )
456 : : {
457 [ + - ][ + - ]: 2 : delete m_pStorageFile;
458 : 2 : m_pStorageFile = NULL;
459 : : }
460 : :
461 [ + - ]: 2 : if( mComponent.is() )
462 : : {
463 : : //mComponent->removeEventListener(this);
464 [ + - ]: 2 : mComponent = Reference< XComponent >();
465 [ + - ]: 2 : }
466 : 2 : }
467 : :
468 : : //-------------------------------------------------------------------------
469 : :
470 : 40 : vector< ::rtl::OUString > PasswordContainer::DecodePasswords( const ::rtl::OUString& aLine, const ::rtl::OUString& aMasterPasswd ) throw(RuntimeException)
471 : : {
472 [ + - ]: 40 : if( !aMasterPasswd.isEmpty() )
473 : : {
474 : 40 : rtlCipher aDecoder = rtl_cipher_create (rtl_Cipher_AlgorithmBF, rtl_Cipher_ModeStream );
475 : : OSL_ENSURE( aDecoder, "Can't create decoder\n" );
476 : :
477 [ + - ]: 40 : if( aDecoder )
478 : : {
479 : : OSL_ENSURE( aMasterPasswd.getLength() == RTL_DIGEST_LENGTH_MD5 * 2, "Wrong master password format!\n" );
480 : :
481 : : unsigned char code[RTL_DIGEST_LENGTH_MD5];
482 [ + + ]: 680 : for( int ind = 0; ind < RTL_DIGEST_LENGTH_MD5; ind++ )
483 : 640 : code[ ind ] = (char)(aMasterPasswd.copy( ind*2, 2 ).toInt32(16));
484 : :
485 : : rtlCipherError result = rtl_cipher_init (
486 : : aDecoder, rtl_Cipher_DirectionDecode,
487 : 40 : code, RTL_DIGEST_LENGTH_MD5, NULL, 0 );
488 : :
489 [ + - ]: 40 : if( result == rtl_Cipher_E_None )
490 : : {
491 [ + - ]: 40 : ::rtl::ByteSequence aSeq = getBufFromAsciiLine( aLine );
492 : :
493 [ + - ]: 40 : ::rtl::ByteSequence resSeq( aSeq.getLength() );
494 : :
495 [ + - ]: 40 : result = rtl_cipher_decode ( aDecoder, (sal_uInt8*)aSeq.getArray(), aSeq.getLength(),
496 [ + - ]: 80 : (sal_uInt8*)resSeq.getArray(), resSeq.getLength() );
497 : :
498 [ + - ][ + - ]: 40 : ::rtl::OUString aPasswd( ( sal_Char* )resSeq.getArray(), resSeq.getLength(), RTL_TEXTENCODING_UTF8 );
499 : :
500 : 40 : rtl_cipher_destroy (aDecoder);
501 : :
502 [ + - ]: 40 : return getInfoFromInd( aPasswd );
503 : : }
504 : :
505 : 0 : rtl_cipher_destroy (aDecoder);
506 : : }
507 : : }
508 : : else
509 : : {
510 : : OSL_FAIL( "No master password provided!\n" );
511 : : // throw special exception
512 : : }
513 : :
514 : : // problems with decoding
515 : : OSL_FAIL( "Problem with decoding\n" );
516 [ # # ]: 0 : throw RuntimeException( ::rtl::OUString("Can't decode!"), Reference< XInterface >() );
517 : : }
518 : :
519 : :
520 : : //-------------------------------------------------------------------------
521 : :
522 : 54 : ::rtl::OUString PasswordContainer::EncodePasswords( vector< ::rtl::OUString > lines, const ::rtl::OUString& aMasterPasswd ) throw(RuntimeException)
523 : : {
524 [ + - ]: 54 : if( !aMasterPasswd.isEmpty() )
525 : : {
526 [ + - ][ + - ]: 54 : ::rtl::OString aSeq = ::rtl::OUStringToOString( createIndex( lines ), RTL_TEXTENCODING_UTF8 );
[ + - ]
527 : :
528 : 54 : rtlCipher aEncoder = rtl_cipher_create (rtl_Cipher_AlgorithmBF, rtl_Cipher_ModeStream );
529 : : OSL_ENSURE( aEncoder, "Can't create encoder\n" );
530 : :
531 [ + - ]: 54 : if( aEncoder )
532 : : {
533 : : OSL_ENSURE( aMasterPasswd.getLength() == RTL_DIGEST_LENGTH_MD5 * 2, "Wrong master password format!\n" );
534 : :
535 : : unsigned char code[RTL_DIGEST_LENGTH_MD5];
536 [ + + ]: 918 : for( int ind = 0; ind < RTL_DIGEST_LENGTH_MD5; ind++ )
537 : 864 : code[ ind ] = (char)(aMasterPasswd.copy( ind*2, 2 ).toInt32(16));
538 : :
539 : : rtlCipherError result = rtl_cipher_init (
540 : : aEncoder, rtl_Cipher_DirectionEncode,
541 : 54 : code, RTL_DIGEST_LENGTH_MD5, NULL, 0 );
542 : :
543 [ + - ]: 54 : if( result == rtl_Cipher_E_None )
544 : : {
545 [ + - ]: 54 : ::rtl::ByteSequence resSeq(aSeq.getLength()+1);
546 : :
547 : 54 : result = rtl_cipher_encode ( aEncoder, (sal_uInt8*)aSeq.getStr(), aSeq.getLength()+1,
548 [ + - ]: 108 : (sal_uInt8*)resSeq.getArray(), resSeq.getLength() );
549 : :
550 : : /*
551 : : //test
552 : : rtlCipherError result = rtl_cipher_init (
553 : : aEncoder, rtl_Cipher_DirectionDecode,
554 : : code, RTL_DIGEST_LENGTH_MD5, NULL, 0 );
555 : :
556 : :
557 : : if( result == rtl_Cipher_E_None )
558 : : {
559 : : ::rtl::OUString testOU = getAsciiLine( resSeq );
560 : : ::rtl::ByteSequence aSeq1 = getBufFromAsciiLine( testOU );
561 : :
562 : : ::rtl::ByteSequence resSeq1( aSeq1.getLength() );
563 : :
564 : : if( resSeq.getLength() == aSeq1.getLength() )
565 : : {
566 : : for( int ind = 0; ind < aSeq1.getLength(); ind++ )
567 : : if( resSeq[ind] != aSeq1[ind] )
568 : : testOU = ::rtl::OUString();
569 : : }
570 : :
571 : : result = rtl_cipher_decode ( aEncoder, (sal_uInt8*)aSeq1.getArray(), aSeq1.getLength(),
572 : : (sal_uInt8*)resSeq1.getArray(), resSeq1.getLength() );
573 : :
574 : : ::rtl::OUString aPasswd( ( sal_Char* )resSeq1.getArray(), resSeq1.getLength(), RTL_TEXTENCODING_UTF8 );
575 : : }
576 : : */
577 : :
578 : 54 : rtl_cipher_destroy (aEncoder);
579 : :
580 [ + - ]: 54 : if( result == rtl_Cipher_E_None )
581 [ + - ][ - + ]: 108 : return getAsciiLine( resSeq );
582 : :
583 : : }
584 : :
585 : 0 : rtl_cipher_destroy (aEncoder);
586 [ - + ]: 54 : }
587 : : }
588 : : else
589 : : {
590 : : OSL_FAIL( "No master password provided!\n" );
591 : : // throw special exception
592 : : }
593 : :
594 : : // problems with encoding
595 : : OSL_FAIL( "Problem with encoding\n" );
596 [ # # ]: 0 : throw RuntimeException( ::rtl::OUString("Can't encode!"), Reference< XInterface >() );
597 : : }
598 : :
599 : : //-------------------------------------------------------------------------
600 : :
601 : 84 : void PasswordContainer::UpdateVector( const ::rtl::OUString& aURL, list< NamePassRecord >& toUpdate, NamePassRecord& aRecord, sal_Bool writeFile ) throw(RuntimeException)
602 : : {
603 [ + + ]: 714 : for( list< NamePassRecord >::iterator aNPIter = toUpdate.begin(); aNPIter != toUpdate.end(); ++aNPIter )
604 [ - + ]: 630 : if( aNPIter->GetUserName().equals( aRecord.GetUserName() ) )
605 : : {
606 [ # # ]: 0 : if( aRecord.HasPasswords( MEMORY_RECORD ) )
607 [ # # ][ # # ]: 0 : aNPIter->SetMemPasswords( aRecord.GetMemPasswords() );
608 : :
609 [ # # ]: 0 : if( aRecord.HasPasswords( PERSISTENT_RECORD ) )
610 : : {
611 : 0 : aNPIter->SetPersPasswords( aRecord.GetPersPasswords() );
612 : :
613 [ # # ]: 0 : if( writeFile )
614 : : {
615 : : // the password must be already encoded
616 [ # # ]: 0 : m_pStorageFile->update( aURL, aRecord ); // change existing ( aURL, aName ) record in the configfile
617 : : }
618 : : }
619 : :
620 : 84 : return;
621 : : }
622 : :
623 : :
624 [ + + ][ + - ]: 84 : if( aRecord.HasPasswords( PERSISTENT_RECORD ) && writeFile )
[ + + ]
625 : : {
626 : : // the password must be already encoded
627 : 46 : m_pStorageFile->update( aURL, aRecord ); // add new aName to the existing url
628 : : }
629 : :
630 : 84 : toUpdate.insert( toUpdate.begin(), aRecord );
631 : : }
632 : :
633 : : //-------------------------------------------------------------------------
634 : :
635 : 70 : UserRecord PasswordContainer::CopyToUserRecord( const NamePassRecord& aRecord, sal_Bool& io_bTryToDecode, const Reference< XInteractionHandler >& aHandler )
636 : : {
637 [ + - ]: 70 : ::std::vector< ::rtl::OUString > aPasswords;
638 [ + + ]: 70 : if( aRecord.HasPasswords( MEMORY_RECORD ) )
639 [ + - ]: 40 : aPasswords = aRecord.GetMemPasswords();
640 : :
641 [ + - ][ + + ]: 70 : if( io_bTryToDecode && aRecord.HasPasswords( PERSISTENT_RECORD ) )
[ + + ]
642 : : {
643 : : try
644 : : {
645 [ + - ][ + - ]: 30 : ::std::vector< ::rtl::OUString > aDecodedPasswords = DecodePasswords( aRecord.GetPersPasswords(), GetMasterPassword( aHandler ) );
646 [ # # ][ + - ]: 30 : aPasswords.insert( aPasswords.end(), aDecodedPasswords.begin(), aDecodedPasswords.end() );
647 : : }
648 [ # # ]: 0 : catch( NoMasterException& )
649 : : {
650 : : // if master password could not be detected the entry will be just ignored
651 : 0 : io_bTryToDecode = sal_False;
652 : : }
653 : : }
654 : :
655 [ + - ][ + - ]: 70 : return UserRecord( aRecord.GetUserName(), copyVectorToSequence( aPasswords ) );
[ + - ]
656 : : }
657 : :
658 : : //-------------------------------------------------------------------------
659 : :
660 : 10 : Sequence< UserRecord > PasswordContainer::CopyToUserRecordSequence( const list< NamePassRecord >& original, const Reference< XInteractionHandler >& aHandler ) throw(RuntimeException)
661 : : {
662 [ + - ]: 10 : Sequence< UserRecord > aResult( original.size() );
663 : 10 : sal_uInt32 nInd = 0;
664 : 10 : sal_Bool bTryToDecode = sal_True;
665 : :
666 [ + + ]: 160 : for( list< NamePassRecord >::const_iterator aNPIter = original.begin();
667 : 80 : aNPIter != original.end();
668 : : ++aNPIter, ++nInd )
669 : : {
670 [ + - ][ + - ]: 70 : aResult[nInd] = CopyToUserRecord( *aNPIter, bTryToDecode, aHandler );
[ + - ][ + - ]
671 : : }
672 : :
673 : 10 : return aResult;
674 : : }
675 : :
676 : : //-------------------------------------------------------------------------
677 : :
678 : 40 : void SAL_CALL PasswordContainer::add( const ::rtl::OUString& Url, const ::rtl::OUString& UserName, const Sequence< ::rtl::OUString >& Passwords, const Reference< XInteractionHandler >& aHandler ) throw(RuntimeException)
679 : : {
680 [ + - ]: 40 : ::osl::MutexGuard aGuard( mMutex );
681 : :
682 [ + - ][ + - ]: 40 : PrivateAdd( Url, UserName, Passwords, MEMORY_RECORD, aHandler );
683 : 40 : }
684 : :
685 : : //-------------------------------------------------------------------------
686 : :
687 : 50 : void SAL_CALL PasswordContainer::addPersistent( const ::rtl::OUString& Url, const ::rtl::OUString& UserName, const Sequence< ::rtl::OUString >& Passwords, const Reference< XInteractionHandler >& aHandler ) throw(RuntimeException)
688 : : {
689 [ + - ]: 50 : ::osl::MutexGuard aGuard( mMutex );
690 : :
691 [ + - ][ + - ]: 50 : PrivateAdd( Url, UserName, Passwords, PERSISTENT_RECORD, aHandler );
692 : 50 : }
693 : :
694 : : //-------------------------------------------------------------------------
695 : :
696 : 90 : void PasswordContainer::PrivateAdd( const ::rtl::OUString& Url, const ::rtl::OUString& UserName, const Sequence< ::rtl::OUString >& Passwords, char Mode, const Reference< XInteractionHandler >& aHandler ) throw(RuntimeException)
697 : : {
698 [ + - ]: 90 : NamePassRecord aRecord( UserName );
699 [ + - ]: 90 : ::std::vector< ::rtl::OUString > aStorePass = copySequenceToVector( Passwords );
700 : :
701 [ + + ]: 90 : if( Mode == PERSISTENT_RECORD )
702 [ + - ][ + - ]: 50 : aRecord.SetPersPasswords( EncodePasswords( aStorePass, GetMasterPassword( aHandler ) ) );
[ + - ]
703 [ + - ]: 40 : else if( Mode == MEMORY_RECORD )
704 [ + - ]: 40 : aRecord.SetMemPasswords( aStorePass );
705 : : else
706 : : {
707 : : OSL_FAIL( "Unexpected persistence status!" );
708 : : return;
709 : : }
710 : :
711 [ + + ]: 90 : if( !m_aContainer.empty() )
712 : : {
713 [ + - ]: 84 : PassMap::iterator aIter = m_aContainer.find( Url );
714 : :
715 [ + - ]: 84 : if( aIter != m_aContainer.end() )
716 : : {
717 [ + - ]: 84 : UpdateVector( aIter->first, aIter->second, aRecord, sal_True );
718 : : return;
719 : : }
720 : : }
721 : :
722 [ + - ]: 6 : list< NamePassRecord > listToAdd( 1, aRecord );
723 [ + - ][ + - ]: 6 : m_aContainer.insert( PairUrlRecord( Url, listToAdd ) );
724 : :
725 [ + - ][ + - ]: 6 : if( Mode == PERSISTENT_RECORD && m_pStorageFile && m_pStorageFile->useStorage() )
[ + - ][ + + ]
[ + + ]
726 [ + - ][ + + ]: 90 : m_pStorageFile->update( Url, aRecord );
[ + + ]
727 : :
728 : : }
729 : :
730 : : //-------------------------------------------------------------------------
731 : :
732 : :
733 : 10 : UrlRecord SAL_CALL PasswordContainer::find( const ::rtl::OUString& aURL, const Reference< XInteractionHandler >& aHandler ) throw(RuntimeException)
734 : : {
735 [ + - ]: 10 : return find( aURL, rtl::OUString(), false, aHandler );
736 : : }
737 : :
738 : : //-------------------------------------------------------------------------
739 : :
740 : 0 : UrlRecord SAL_CALL PasswordContainer::findForName( const ::rtl::OUString& aURL, const ::rtl::OUString& aName, const Reference< XInteractionHandler >& aHandler ) throw(RuntimeException)
741 : : {
742 : 0 : return find( aURL, aName, true, aHandler );
743 : : }
744 : :
745 : : //-------------------------------------------------------------------------
746 : :
747 : 0 : Sequence< UserRecord > PasswordContainer::FindUsr( const list< NamePassRecord >& userlist, const ::rtl::OUString& aName, const Reference< XInteractionHandler >& aHandler ) throw(RuntimeException)
748 : : {
749 : 0 : sal_uInt32 nInd = 0;
750 [ # # ]: 0 : for( list< NamePassRecord >::const_iterator aNPIter = userlist.begin();
751 : 0 : aNPIter != userlist.end();
752 : : ++aNPIter, ++nInd )
753 : : {
754 [ # # ]: 0 : if( aNPIter->GetUserName().equals( aName ) )
755 : : {
756 [ # # ]: 0 : Sequence< UserRecord > aResult(1);
757 : 0 : sal_Bool bTryToDecode = sal_True;
758 [ # # ][ # # ]: 0 : aResult[0] = CopyToUserRecord( *aNPIter, bTryToDecode, aHandler );
[ # # ][ # # ]
759 : :
760 [ # # ][ # # ]: 0 : return aResult;
761 : : }
762 : : }
763 : :
764 : 0 : return Sequence< UserRecord >();
765 : : }
766 : :
767 : : //-------------------------------------------------------------------------
768 : :
769 : 10 : bool PasswordContainer::createUrlRecord(
770 : : const PassMap::iterator & rIter,
771 : : bool bName,
772 : : const ::rtl::OUString & aName,
773 : : const Reference< XInteractionHandler >& aHandler,
774 : : UrlRecord & rRec )
775 : : throw( RuntimeException )
776 : : {
777 [ - + ]: 10 : if ( bName )
778 : : {
779 : : Sequence< UserRecord > aUsrRec
780 [ # # ]: 0 : = FindUsr( rIter->second, aName, aHandler );
781 [ # # ]: 0 : if( aUsrRec.getLength() )
782 : : {
783 [ # # ][ # # ]: 0 : rRec = UrlRecord( rIter->first, aUsrRec );
[ # # ]
784 : 0 : return true;
785 [ # # ][ # # ]: 0 : }
786 : : }
787 : : else
788 : : {
789 : : rRec = UrlRecord(
790 : 10 : rIter->first,
791 [ + - ][ + - ]: 20 : CopyToUserRecordSequence( rIter->second, aHandler ) );
[ + - ]
792 : 10 : return true;
793 : : }
794 : 0 : return false;
795 : : }
796 : :
797 : : //-------------------------------------------------------------------------
798 : :
799 : 10 : UrlRecord PasswordContainer::find(
800 : : const ::rtl::OUString& aURL,
801 : : const ::rtl::OUString& aName,
802 : : bool bName, // only needed to support empty user names
803 : : const Reference< XInteractionHandler >& aHandler ) throw(RuntimeException)
804 : : {
805 [ + - ]: 10 : ::osl::MutexGuard aGuard( mMutex );
806 : :
807 [ + - ][ + - ]: 10 : if( !m_aContainer.empty() && !aURL.isEmpty() )
[ + - ]
808 : : {
809 : 10 : ::rtl::OUString aUrl( aURL );
810 : :
811 : : // each iteration remove last '/...' section from the aUrl
812 : : // while it's possible, up to the most left '://'
813 [ # # # # ]: 0 : do
[ # # ]
814 : : {
815 : : // first look for <url>/somename and then look for <url>/somename/...
816 [ + - ]: 10 : PassMap::iterator aIter = m_aContainer.find( aUrl );
817 [ + - ]: 10 : if( aIter != m_aContainer.end() )
818 : : {
819 [ + - ]: 10 : UrlRecord aRec;
820 [ + - ][ + - ]: 10 : if ( createUrlRecord( aIter, bName, aName, aHandler, aRec ) )
821 [ + - ][ + - ]: 10 : return aRec;
[ - + ]
822 : : }
823 : : else
824 : : {
825 : 0 : ::rtl::OUString tmpUrl( aUrl );
826 [ # # ]: 0 : if ( tmpUrl.getStr()[tmpUrl.getLength() - 1] != (sal_Unicode)'/' )
827 : 0 : tmpUrl += ::rtl::OUString("/");
828 : :
829 [ # # ]: 0 : aIter = m_aContainer.lower_bound( tmpUrl );
830 [ # # ][ # # ]: 0 : if( aIter != m_aContainer.end() && aIter->first.match( tmpUrl ) )
[ # # ][ # # ]
831 : : {
832 [ # # ]: 0 : UrlRecord aRec;
833 [ # # ][ # # ]: 0 : if ( createUrlRecord( aIter, bName, aName, aHandler, aRec ) )
834 [ # # ][ # # ]: 0 : return aRec;
[ # # ]
835 [ # # ]: 0 : }
836 : : }
837 : : }
838 [ # # ][ - + ]: 10 : while( shorterUrl( aUrl ) && !aUrl.isEmpty() );
839 : : }
840 : :
841 [ # # ][ + - ]: 10 : return UrlRecord();
842 : : }
843 : :
844 : : //-------------------------------------------------------------------------
845 : 0 : ::rtl::OUString PasswordContainer::GetDefaultMasterPassword()
846 : : {
847 : 0 : ::rtl::OUString aResult;
848 [ # # ]: 0 : for ( sal_Int32 nInd = 0; nInd < RTL_DIGEST_LENGTH_MD5; nInd++ )
849 : 0 : aResult += ::rtl::OUString( "aa" );
850 : :
851 : 0 : return aResult;
852 : : }
853 : :
854 : : //-------------------------------------------------------------------------
855 : 4 : ::rtl::OUString PasswordContainer::RequestPasswordFromUser( PasswordRequestMode aRMode, const uno::Reference< task::XInteractionHandler >& xHandler )
856 : : {
857 : : // empty string means that the call was cancelled or just failed
858 : 4 : ::rtl::OUString aResult;
859 : :
860 [ + - ]: 4 : if ( xHandler.is() )
861 : : {
862 [ + - ]: 4 : ::rtl::Reference< MasterPasswordRequest_Impl > xRequest = new MasterPasswordRequest_Impl( aRMode );
863 : :
864 [ + - ][ + - ]: 4 : xHandler->handle( xRequest.get() );
[ + - ][ + - ]
865 : :
866 [ + - ]: 4 : ::rtl::Reference< ucbhelper::InteractionContinuation > xSelection = xRequest->getSelection();
867 : :
868 [ + - ]: 4 : if ( xSelection.is() )
869 : : {
870 [ + - ]: 4 : Reference< XInteractionAbort > xAbort( xSelection.get(), UNO_QUERY );
871 [ + - ]: 4 : if ( !xAbort.is() )
872 : : {
873 : : const ::rtl::Reference< ucbhelper::InteractionSupplyAuthentication > & xSupp
874 : 4 : = xRequest->getAuthenticationSupplier();
875 : :
876 : 4 : aResult = xSupp->getPassword();
877 : 4 : }
878 : 4 : }
879 : : }
880 : :
881 : 4 : return aResult;
882 : : }
883 : :
884 : : //-------------------------------------------------------------------------
885 : :
886 : 90 : ::rtl::OUString PasswordContainer::GetMasterPassword( const Reference< XInteractionHandler >& aHandler ) throw(RuntimeException)
887 : : {
888 : 90 : PasswordRequestMode aRMode = PasswordRequestMode_PASSWORD_ENTER;
889 [ + - ][ + - ]: 90 : if( !m_pStorageFile || !m_pStorageFile->useStorage() )
[ - + ][ - + ]
890 [ # # ]: 0 : throw NoMasterException( ::rtl::OUString("Password storing is not active!"), Reference< XInterface >(), aRMode );
891 : :
892 [ + + ][ + - ]: 90 : if( m_aMasterPasswd.isEmpty() && aHandler.is() )
[ + + ]
893 : : {
894 : 4 : ::rtl::OUString aEncodedMP;
895 : 4 : sal_Bool bAskAgain = sal_False;
896 : 4 : sal_Bool bDefaultPassword = sal_False;
897 : :
898 [ + - ][ + - ]: 4 : if( !m_pStorageFile->getEncodedMP( aEncodedMP ) )
899 : 4 : aRMode = PasswordRequestMode_PASSWORD_CREATE;
900 [ # # ]: 0 : else if ( aEncodedMP.isEmpty() )
901 : : {
902 [ # # ]: 0 : m_aMasterPasswd = GetDefaultMasterPassword();
903 : 0 : bDefaultPassword = sal_True;
904 : : }
905 : :
906 [ + - ]: 4 : if ( !bDefaultPassword )
907 : : {
908 [ - + ]: 4 : do {
909 : 4 : bAskAgain = sal_False;
910 : :
911 [ + - ]: 4 : ::rtl::OUString aPass = RequestPasswordFromUser( aRMode, aHandler );
912 [ + - ]: 4 : if ( !aPass.isEmpty() )
913 : : {
914 [ + - ]: 4 : if( aRMode == PasswordRequestMode_PASSWORD_CREATE )
915 : : {
916 : 4 : m_aMasterPasswd = aPass;
917 [ + - ]: 4 : vector< ::rtl::OUString > aMaster( 1, m_aMasterPasswd );
918 : :
919 [ + - ][ + - ]: 4 : m_pStorageFile->setEncodedMP( EncodePasswords( aMaster, m_aMasterPasswd ) );
[ + - ]
920 : : }
921 : : else
922 : : {
923 [ # # ]: 0 : vector< ::rtl::OUString > aRM( DecodePasswords( aEncodedMP, aPass ) );
924 [ # # ][ # # ]: 0 : if( aRM.empty() || !aPass.equals( aRM[0] ) )
[ # # ]
925 : : {
926 : 0 : bAskAgain = sal_True;
927 : 0 : aRMode = PasswordRequestMode_PASSWORD_REENTER;
928 : : }
929 : : else
930 : 0 : m_aMasterPasswd = aPass;
931 : : }
932 : 4 : }
933 : :
934 : : } while( bAskAgain );
935 : 4 : }
936 : : }
937 : :
938 [ - + ]: 90 : if ( m_aMasterPasswd.isEmpty() )
939 [ # # ]: 0 : throw NoMasterException( ::rtl::OUString("No master password!"), Reference< XInterface >(), aRMode );
940 : :
941 : 90 : return m_aMasterPasswd;
942 : : }
943 : :
944 : : //-------------------------------------------------------------------------
945 : :
946 : 70 : void SAL_CALL PasswordContainer::remove( const ::rtl::OUString& aURL, const ::rtl::OUString& aName ) throw(RuntimeException)
947 : : {
948 [ + - ]: 70 : ::osl::MutexGuard aGuard( mMutex );
949 : :
950 : 70 : ::rtl::OUString aUrl( aURL );
951 [ + + ]: 70 : if( !m_aContainer.empty() )
952 : : {
953 [ + - ]: 60 : PassMap::iterator aIter = m_aContainer.find( aUrl );
954 : :
955 [ - + ]: 60 : if( aIter == m_aContainer.end() )
956 : : {
957 : 0 : sal_Int32 aInd = aUrl.lastIndexOf( sal_Unicode( '/' ) );
958 [ # # ][ # # ]: 0 : if( aInd > 0 && aUrl.getLength()-1 == aInd )
[ # # ]
959 : 0 : aUrl = aUrl.copy( 0, aUrl.getLength() - 1 );
960 : : else
961 : 0 : aUrl += ::rtl::OUString("/");
962 : :
963 [ # # ]: 0 : aIter = m_aContainer.find( aUrl );
964 : : }
965 : :
966 [ + - ]: 60 : if( aIter != m_aContainer.end() )
967 : : {
968 [ + - ]: 510 : for( list< NamePassRecord >::iterator aNPIter = aIter->second.begin(); aNPIter != aIter->second.end(); ++aNPIter )
969 [ + + ]: 440 : if( aNPIter->GetUserName().equals( aName ) )
970 : : {
971 [ + + ][ + - ]: 60 : if( aNPIter->HasPasswords( PERSISTENT_RECORD ) && m_pStorageFile )
[ + + ]
972 [ + - ]: 20 : m_pStorageFile->remove( aURL, aName ); // remove record ( aURL, aName )
973 : :
974 : : // the iterator will not be used any more so it can be removed directly
975 [ + - ]: 60 : aIter->second.erase( aNPIter );
976 : :
977 [ + + ]: 60 : if( aIter->second.begin() == aIter->second.end() )
978 [ + - ]: 4 : m_aContainer.erase( aIter );
979 : :
980 : 70 : return;
981 : : }
982 : : }
983 [ + + ][ + - ]: 70 : }
[ + + ]
984 : : }
985 : :
986 : : //-------------------------------------------------------------------------
987 : :
988 : 0 : void SAL_CALL PasswordContainer::removePersistent( const ::rtl::OUString& aURL, const ::rtl::OUString& aName ) throw(RuntimeException)
989 : : {
990 [ # # ]: 0 : ::osl::MutexGuard aGuard( mMutex );
991 : :
992 : 0 : ::rtl::OUString aUrl( aURL );
993 [ # # ]: 0 : if( !m_aContainer.empty() )
994 : : {
995 [ # # ]: 0 : PassMap::iterator aIter = m_aContainer.find( aUrl );
996 : :
997 [ # # ]: 0 : if( aIter == m_aContainer.end() )
998 : : {
999 : 0 : sal_Int32 aInd = aUrl.lastIndexOf( sal_Unicode( '/' ) );
1000 [ # # ][ # # ]: 0 : if( aInd > 0 && aUrl.getLength()-1 == aInd )
[ # # ]
1001 : 0 : aUrl = aUrl.copy( 0, aUrl.getLength() - 1 );
1002 : : else
1003 : 0 : aUrl += ::rtl::OUString("/");
1004 : :
1005 [ # # ]: 0 : aIter = m_aContainer.find( aUrl );
1006 : : }
1007 : :
1008 [ # # ]: 0 : if( aIter != m_aContainer.end() )
1009 : : {
1010 [ # # ]: 0 : for( list< NamePassRecord >::iterator aNPIter = aIter->second.begin(); aNPIter != aIter->second.end(); ++aNPIter )
1011 [ # # ]: 0 : if( aNPIter->GetUserName().equals( aName ) )
1012 : : {
1013 [ # # ]: 0 : if( aNPIter->HasPasswords( PERSISTENT_RECORD ) )
1014 : : {
1015 : : // TODO/LATER: should the password be converted to MemoryPassword?
1016 : 0 : aNPIter->RemovePasswords( PERSISTENT_RECORD );
1017 : :
1018 [ # # ]: 0 : if ( m_pStorageFile )
1019 [ # # ]: 0 : m_pStorageFile->remove( aURL, aName ); // remove record ( aURL, aName )
1020 : : }
1021 : :
1022 [ # # ]: 0 : if( !aNPIter->HasPasswords( MEMORY_RECORD ) )
1023 [ # # ]: 0 : aIter->second.erase( aNPIter );
1024 : :
1025 [ # # ]: 0 : if( aIter->second.begin() == aIter->second.end() )
1026 [ # # ]: 0 : m_aContainer.erase( aIter );
1027 : :
1028 : 0 : return;
1029 : : }
1030 : : }
1031 [ # # ][ # # ]: 0 : }
[ # # ]
1032 : : }
1033 : : //-------------------------------------------------------------------------
1034 : :
1035 : 8 : void SAL_CALL PasswordContainer::removeAllPersistent() throw(RuntimeException)
1036 : : {
1037 [ + - ]: 8 : ::osl::MutexGuard aGuard( mMutex );
1038 : :
1039 [ + - ]: 8 : if( m_pStorageFile )
1040 [ + - ]: 8 : m_pStorageFile->clear();
1041 : :
1042 [ + + ]: 12 : for( PassMap::iterator aIter = m_aContainer.begin(); aIter != m_aContainer.end(); )
1043 : : {
1044 [ + + ]: 44 : for( list< NamePassRecord >::iterator aNPIter = aIter->second.begin(); aNPIter != aIter->second.end(); )
1045 : : {
1046 [ + + ]: 40 : if( aNPIter->HasPasswords( PERSISTENT_RECORD ) )
1047 : : {
1048 : : // TODO/LATER: should the password be converted to MemoryPassword?
1049 : 30 : aNPIter->RemovePasswords( PERSISTENT_RECORD );
1050 : :
1051 [ + - ]: 30 : if ( m_pStorageFile )
1052 [ + - ]: 30 : m_pStorageFile->remove( aIter->first, aNPIter->GetUserName() ); // remove record ( aURL, aName )
1053 : : }
1054 : :
1055 [ + + ]: 40 : if( !aNPIter->HasPasswords( MEMORY_RECORD ) )
1056 : : {
1057 : 30 : list< NamePassRecord >::iterator aIterToDelete( aNPIter );
1058 : 30 : ++aNPIter;
1059 [ + - ]: 30 : aIter->second.erase( aIterToDelete );
1060 : : }
1061 : : else
1062 : 10 : ++aNPIter;
1063 : : }
1064 : :
1065 [ + + ]: 4 : if( aIter->second.begin() == aIter->second.end() )
1066 : : {
1067 : 2 : PassMap::iterator aIterToDelete( aIter );
1068 : 2 : ++aIter;
1069 [ + - ]: 2 : m_aContainer.erase( aIterToDelete );
1070 : : }
1071 : : else
1072 : 2 : ++aIter;
1073 [ + - ]: 8 : }
1074 : 8 : }
1075 : : //-------------------------------------------------------------------------
1076 : :
1077 : 2 : Sequence< UrlRecord > SAL_CALL PasswordContainer::getAllPersistent( const Reference< XInteractionHandler >& xHandler ) throw(RuntimeException)
1078 : : {
1079 [ + - ]: 2 : Sequence< UrlRecord > aResult;
1080 : :
1081 [ + - ]: 2 : ::osl::MutexGuard aGuard( mMutex );
1082 [ + + ]: 4 : for( PassMap::iterator aIter = m_aContainer.begin(); aIter != m_aContainer.end(); ++aIter )
1083 : : {
1084 [ + - ]: 2 : Sequence< UserRecord > aUsers;
1085 [ + + ]: 12 : for( list< NamePassRecord >::iterator aNPIter = aIter->second.begin(); aNPIter != aIter->second.end(); ++aNPIter )
1086 [ + - ]: 10 : if( aNPIter->HasPasswords( PERSISTENT_RECORD ) )
1087 : : {
1088 : 10 : sal_Int32 oldLen = aUsers.getLength();
1089 [ + - ]: 10 : aUsers.realloc( oldLen + 1 );
1090 [ + - ][ + - ]: 10 : aUsers[ oldLen ] = UserRecord( aNPIter->GetUserName(), copyVectorToSequence( DecodePasswords( aNPIter->GetPersPasswords(), GetMasterPassword( xHandler ) ) ) );
[ + - ][ + - ]
[ + - ][ + - ]
[ + - ][ + - ]
1091 : : }
1092 : :
1093 [ + - ]: 2 : if( aUsers.getLength() )
1094 : : {
1095 : 2 : sal_Int32 oldLen = aResult.getLength();
1096 [ + - ]: 2 : aResult.realloc( oldLen + 1 );
1097 [ + - ][ + - ]: 2 : aResult[ oldLen ] = UrlRecord( aIter->first, aUsers );
[ + - ][ + - ]
1098 : : }
1099 [ + - ]: 2 : }
1100 : :
1101 [ + - ]: 2 : return aResult;
1102 : : }
1103 : :
1104 : : //-------------------------------------------------------------------------
1105 : 0 : sal_Bool SAL_CALL PasswordContainer::authorizateWithMasterPassword( const uno::Reference< task::XInteractionHandler >& xHandler )
1106 : : throw (uno::RuntimeException)
1107 : : {
1108 : 0 : sal_Bool bResult = sal_False;
1109 : 0 : ::rtl::OUString aEncodedMP;
1110 : 0 : uno::Reference< task::XInteractionHandler > xTmpHandler = xHandler;
1111 [ # # ]: 0 : ::osl::MutexGuard aGuard( mMutex );
1112 : :
1113 : : // the method should fail if there is no master password
1114 [ # # ][ # # ]: 0 : if( m_pStorageFile && m_pStorageFile->useStorage() && m_pStorageFile->getEncodedMP( aEncodedMP ) )
[ # # ][ # # ]
[ # # ][ # # ]
1115 : : {
1116 [ # # ]: 0 : if ( aEncodedMP.isEmpty() )
1117 : : {
1118 : : // this is a default master password
1119 : : // no UI is necessary
1120 : 0 : bResult = sal_True;
1121 : : }
1122 : : else
1123 : : {
1124 [ # # ]: 0 : if ( !xTmpHandler.is() )
1125 : : {
1126 [ # # ]: 0 : uno::Reference< lang::XMultiServiceFactory > xFactory( mComponent, uno::UNO_QUERY_THROW );
1127 [ # # ][ # # ]: 0 : xTmpHandler.set( xFactory->createInstance( ::rtl::OUString( "com.sun.star.task.InteractionHandler" ) ), uno::UNO_QUERY_THROW );
[ # # ]
1128 : : }
1129 : :
1130 [ # # ]: 0 : if ( !m_aMasterPasswd.isEmpty() )
1131 : : {
1132 : : // there is a password, it should be just rechecked
1133 : 0 : PasswordRequestMode aRMode = PasswordRequestMode_PASSWORD_ENTER;
1134 : 0 : ::rtl::OUString aPass;
1135 : :
1136 [ # # # # ]: 0 : do {
[ # # ]
1137 [ # # ]: 0 : aPass = RequestPasswordFromUser( aRMode, xTmpHandler );
1138 [ # # ][ # # ]: 0 : bResult = ( !aPass.isEmpty() && aPass.equals( m_aMasterPasswd ) );
1139 : 0 : aRMode = PasswordRequestMode_PASSWORD_REENTER; // further questions with error notification
1140 [ # # ]: 0 : } while( !bResult && !aPass.isEmpty() );
1141 : : }
1142 : : else
1143 : : {
1144 : : try
1145 : : {
1146 : : // ask for the password, if user provide no correct password an exception will be thrown
1147 [ # # ]: 0 : bResult = !GetMasterPassword( xTmpHandler ).isEmpty();
1148 : : }
1149 [ # # ]: 0 : catch( uno::Exception& )
1150 : : {}
1151 : : }
1152 : : }
1153 : : }
1154 : :
1155 [ # # ]: 0 : return bResult;
1156 : : }
1157 : :
1158 : : //-------------------------------------------------------------------------
1159 : 0 : sal_Bool SAL_CALL PasswordContainer::changeMasterPassword( const uno::Reference< task::XInteractionHandler >& xHandler )
1160 : : throw (uno::RuntimeException)
1161 : : {
1162 : 0 : sal_Bool bResult = sal_False;
1163 : 0 : uno::Reference< task::XInteractionHandler > xTmpHandler = xHandler;
1164 [ # # ]: 0 : ::osl::MutexGuard aGuard( mMutex );
1165 : :
1166 [ # # ][ # # ]: 0 : if ( m_pStorageFile && m_pStorageFile->useStorage() )
[ # # ][ # # ]
1167 : : {
1168 [ # # ]: 0 : if ( !xTmpHandler.is() )
1169 : : {
1170 [ # # ]: 0 : uno::Reference< lang::XMultiServiceFactory > xFactory( mComponent, uno::UNO_QUERY_THROW );
1171 [ # # ][ # # ]: 0 : xTmpHandler.set( xFactory->createInstance( ::rtl::OUString( "com.sun.star.task.InteractionHandler" ) ), uno::UNO_QUERY_THROW );
[ # # ]
1172 : : }
1173 : :
1174 : 0 : sal_Bool bCanChangePassword = sal_True;
1175 : : // if there is already a stored master password it should be entered by the user before the change happen
1176 : 0 : ::rtl::OUString aEncodedMP;
1177 [ # # ][ # # ]: 0 : if( !m_aMasterPasswd.isEmpty() || m_pStorageFile->getEncodedMP( aEncodedMP ) )
[ # # ][ # # ]
1178 [ # # ]: 0 : bCanChangePassword = authorizateWithMasterPassword( xTmpHandler );
1179 : :
1180 [ # # ]: 0 : if ( bCanChangePassword )
1181 : : {
1182 : : // ask for the new password, but do not set it
1183 : 0 : PasswordRequestMode aRMode = PasswordRequestMode_PASSWORD_CREATE;
1184 [ # # ]: 0 : ::rtl::OUString aPass = RequestPasswordFromUser( aRMode, xTmpHandler );
1185 : :
1186 [ # # ]: 0 : if ( !aPass.isEmpty() )
1187 : : {
1188 : : // get all the persistent entries if it is possible
1189 [ # # ]: 0 : Sequence< UrlRecord > aPersistent = getAllPersistent( uno::Reference< task::XInteractionHandler >() );
1190 : :
1191 : : // remove the master password and the entries persistence
1192 [ # # ]: 0 : removeMasterPassword();
1193 : :
1194 : : // store the new master password
1195 : 0 : m_aMasterPasswd = aPass;
1196 [ # # ]: 0 : vector< ::rtl::OUString > aMaster( 1, m_aMasterPasswd );
1197 [ # # ][ # # ]: 0 : m_pStorageFile->setEncodedMP( EncodePasswords( aMaster, m_aMasterPasswd ) );
[ # # ]
1198 : :
1199 : : // store all the entries with the new password
1200 [ # # ]: 0 : for ( int nURLInd = 0; nURLInd < aPersistent.getLength(); nURLInd++ )
1201 [ # # ][ # # ]: 0 : for ( int nNameInd = 0; nNameInd< aPersistent[nURLInd].UserList.getLength(); nNameInd++ )
1202 [ # # ]: 0 : addPersistent( aPersistent[nURLInd].Url,
1203 [ # # ][ # # ]: 0 : aPersistent[nURLInd].UserList[nNameInd].UserName,
1204 [ # # ][ # # ]: 0 : aPersistent[nURLInd].UserList[nNameInd].Passwords,
1205 [ # # ]: 0 : uno::Reference< task::XInteractionHandler >() );
1206 : :
1207 [ # # ]: 0 : bResult = sal_True;
1208 : 0 : }
1209 : 0 : }
1210 : : }
1211 : :
1212 [ # # ]: 0 : return bResult;
1213 : : }
1214 : :
1215 : : //-------------------------------------------------------------------------
1216 : 4 : void SAL_CALL PasswordContainer::removeMasterPassword()
1217 : : throw (uno::RuntimeException)
1218 : : {
1219 : : // remove all the stored passwords and the master password
1220 [ + - ]: 4 : removeAllPersistent();
1221 : :
1222 [ + - ]: 4 : ::osl::MutexGuard aGuard( mMutex );
1223 [ + - ]: 4 : if ( m_pStorageFile )
1224 : : {
1225 : 4 : m_aMasterPasswd = ::rtl::OUString();
1226 [ + - ]: 4 : m_pStorageFile->setEncodedMP( ::rtl::OUString() ); // let the master password be removed from configuration
1227 [ + - ]: 4 : }
1228 : 4 : }
1229 : :
1230 : : //-------------------------------------------------------------------------
1231 : 0 : ::sal_Bool SAL_CALL PasswordContainer::hasMasterPassword( )
1232 : : throw (::com::sun::star::uno::RuntimeException)
1233 : : {
1234 [ # # ]: 0 : ::osl::MutexGuard aGuard( mMutex );
1235 : :
1236 [ # # ]: 0 : if ( !m_pStorageFile )
1237 [ # # ]: 0 : throw uno::RuntimeException();
1238 : :
1239 : 0 : ::rtl::OUString aEncodedMP;
1240 [ # # ][ # # ]: 0 : return ( m_pStorageFile->useStorage() && m_pStorageFile->getEncodedMP( aEncodedMP ) );
[ # # ][ # # ]
[ # # ]
1241 : : }
1242 : :
1243 : : //-------------------------------------------------------------------------
1244 : 8 : ::sal_Bool SAL_CALL PasswordContainer::allowPersistentStoring( ::sal_Bool bAllow )
1245 : : throw (::com::sun::star::uno::RuntimeException)
1246 : : {
1247 [ + - ]: 8 : ::osl::MutexGuard aGuard( mMutex );
1248 : :
1249 [ - + ]: 8 : if ( !m_pStorageFile )
1250 [ # # ]: 0 : throw uno::RuntimeException();
1251 : :
1252 [ + + ]: 8 : if ( !bAllow )
1253 [ + - ]: 4 : removeMasterPassword();
1254 : :
1255 [ + - ][ - + ]: 8 : if ( m_pStorageFile->useStorage() == bAllow )
1256 : 0 : return bAllow;
1257 : :
1258 [ + - ]: 8 : m_pStorageFile->setUseStorage( bAllow );
1259 [ + - ]: 8 : return !bAllow;
1260 : : }
1261 : :
1262 : : //-------------------------------------------------------------------------
1263 : 0 : ::sal_Bool SAL_CALL PasswordContainer::isPersistentStoringAllowed()
1264 : : throw (::com::sun::star::uno::RuntimeException)
1265 : : {
1266 [ # # ]: 0 : ::osl::MutexGuard aGuard( mMutex );
1267 : :
1268 [ # # ]: 0 : if ( !m_pStorageFile )
1269 [ # # ]: 0 : throw uno::RuntimeException();
1270 : :
1271 [ # # ][ # # ]: 0 : return m_pStorageFile->useStorage();
1272 : : }
1273 : :
1274 : : //-------------------------------------------------------------------------
1275 : 0 : ::sal_Bool SAL_CALL PasswordContainer::useDefaultMasterPassword( const uno::Reference< task::XInteractionHandler >& xHandler )
1276 : : throw ( uno::RuntimeException )
1277 : : {
1278 : 0 : sal_Bool bResult = sal_False;
1279 : 0 : uno::Reference< task::XInteractionHandler > xTmpHandler = xHandler;
1280 [ # # ]: 0 : ::osl::MutexGuard aGuard( mMutex );
1281 : :
1282 [ # # ][ # # ]: 0 : if ( m_pStorageFile && m_pStorageFile->useStorage() )
[ # # ][ # # ]
1283 : : {
1284 [ # # ]: 0 : if ( !xTmpHandler.is() )
1285 : : {
1286 [ # # ]: 0 : uno::Reference< lang::XMultiServiceFactory > xFactory( mComponent, uno::UNO_QUERY_THROW );
1287 [ # # ][ # # ]: 0 : xTmpHandler.set( xFactory->createInstance( ::rtl::OUString( "com.sun.star.task.InteractionHandler" ) ), uno::UNO_QUERY_THROW );
[ # # ]
1288 : : }
1289 : :
1290 : 0 : sal_Bool bCanChangePassword = sal_True;
1291 : : // if there is already a stored nondefault master password it should be entered by the user before the change happen
1292 : 0 : ::rtl::OUString aEncodedMP;
1293 [ # # ][ # # ]: 0 : if( m_pStorageFile->getEncodedMP( aEncodedMP ) && !aEncodedMP.isEmpty() )
[ # # ][ # # ]
1294 [ # # ]: 0 : bCanChangePassword = authorizateWithMasterPassword( xTmpHandler );
1295 : :
1296 [ # # ]: 0 : if ( bCanChangePassword )
1297 : : {
1298 : : // generate the default password
1299 [ # # ]: 0 : ::rtl::OUString aPass = GetDefaultMasterPassword();
1300 [ # # ]: 0 : if ( !aPass.isEmpty() )
1301 : : {
1302 : : // get all the persistent entries if it is possible
1303 [ # # ]: 0 : Sequence< UrlRecord > aPersistent = getAllPersistent( uno::Reference< task::XInteractionHandler >() );
1304 : :
1305 : : // remove the master password and the entries persistence
1306 [ # # ]: 0 : removeMasterPassword();
1307 : :
1308 : : // store the empty string to flag the default master password
1309 : 0 : m_aMasterPasswd = aPass;
1310 [ # # ]: 0 : m_pStorageFile->setEncodedMP( ::rtl::OUString(), sal_True );
1311 : :
1312 : : // store all the entries with the new password
1313 [ # # ]: 0 : for ( int nURLInd = 0; nURLInd < aPersistent.getLength(); nURLInd++ )
1314 [ # # ][ # # ]: 0 : for ( int nNameInd = 0; nNameInd< aPersistent[nURLInd].UserList.getLength(); nNameInd++ )
1315 [ # # ]: 0 : addPersistent( aPersistent[nURLInd].Url,
1316 [ # # ][ # # ]: 0 : aPersistent[nURLInd].UserList[nNameInd].UserName,
1317 [ # # ][ # # ]: 0 : aPersistent[nURLInd].UserList[nNameInd].Passwords,
1318 [ # # ]: 0 : uno::Reference< task::XInteractionHandler >() );
1319 : :
1320 [ # # ]: 0 : bResult = sal_True;
1321 : 0 : }
1322 : 0 : }
1323 : : }
1324 : :
1325 [ # # ]: 0 : return bResult;
1326 : :
1327 : : }
1328 : :
1329 : : //-------------------------------------------------------------------------
1330 : 0 : ::sal_Bool SAL_CALL PasswordContainer::isDefaultMasterPasswordUsed()
1331 : : throw ( uno::RuntimeException )
1332 : : {
1333 [ # # ]: 0 : ::osl::MutexGuard aGuard( mMutex );
1334 : :
1335 [ # # ]: 0 : if ( !m_pStorageFile )
1336 [ # # ]: 0 : throw uno::RuntimeException();
1337 : :
1338 : 0 : ::rtl::OUString aEncodedMP;
1339 [ # # ][ # # ]: 0 : return ( m_pStorageFile->useStorage() && m_pStorageFile->getEncodedMP( aEncodedMP ) && aEncodedMP.isEmpty() );
[ # # ][ # # ]
[ # # ][ # # ]
1340 : : }
1341 : :
1342 : :
1343 : : //-------------------------------------------------------------------------
1344 : 0 : void SAL_CALL PasswordContainer::addUrl( const ::rtl::OUString& Url, ::sal_Bool MakePersistent )
1345 : : throw (uno::RuntimeException)
1346 : : {
1347 : 0 : mUrlContainer.add( Url, MakePersistent );
1348 : 0 : }
1349 : :
1350 : : //-------------------------------------------------------------------------
1351 : 0 : ::rtl::OUString SAL_CALL PasswordContainer::findUrl( const ::rtl::OUString& Url )
1352 : : throw (uno::RuntimeException)
1353 : : {
1354 : 0 : return mUrlContainer.find( Url );
1355 : : }
1356 : :
1357 : : //-------------------------------------------------------------------------
1358 : 0 : void SAL_CALL PasswordContainer::removeUrl( const ::rtl::OUString& Url )
1359 : : throw (uno::RuntimeException)
1360 : : {
1361 : 0 : mUrlContainer.remove( Url );
1362 : 0 : }
1363 : :
1364 : : //-------------------------------------------------------------------------
1365 : 0 : uno::Sequence< ::rtl::OUString > SAL_CALL PasswordContainer::getUrls( ::sal_Bool OnlyPersistent )
1366 : : throw (uno::RuntimeException)
1367 : : {
1368 : 0 : return mUrlContainer.list( OnlyPersistent );
1369 : : }
1370 : :
1371 : : //-------------------------------------------------------------------------
1372 : :
1373 : 0 : void PasswordContainer::Notify()
1374 : : {
1375 [ # # ]: 0 : ::osl::MutexGuard aGuard( mMutex );
1376 : :
1377 : 0 : PassMap::iterator aIter;
1378 : :
1379 : : // remove the cached persistent values in the memory
1380 [ # # ]: 0 : for( aIter = m_aContainer.begin(); aIter != m_aContainer.end(); ++aIter )
1381 : : {
1382 [ # # ]: 0 : for( list< NamePassRecord >::iterator aNPIter = aIter->second.begin(); aNPIter != aIter->second.end(); )
1383 : : {
1384 [ # # ]: 0 : if( aNPIter->HasPasswords( PERSISTENT_RECORD ) )
1385 : : {
1386 : 0 : aNPIter->RemovePasswords( PERSISTENT_RECORD );
1387 : :
1388 [ # # ]: 0 : if ( m_pStorageFile )
1389 [ # # ]: 0 : m_pStorageFile->remove( aIter->first, aNPIter->GetUserName() ); // remove record ( aURL, aName )
1390 : : }
1391 : :
1392 [ # # ]: 0 : if( !aNPIter->HasPasswords( MEMORY_RECORD ) )
1393 : : {
1394 : 0 : list< NamePassRecord >::iterator aIterToDelete( aNPIter );
1395 : 0 : ++aNPIter;
1396 [ # # ]: 0 : aIter->second.erase( aIterToDelete );
1397 : : }
1398 : : else
1399 : 0 : ++aNPIter;
1400 : : }
1401 : : }
1402 : :
1403 [ # # ]: 0 : PassMap addon;
1404 [ # # ]: 0 : if( m_pStorageFile )
1405 [ # # ][ # # ]: 0 : addon = m_pStorageFile->getInfo();
1406 : :
1407 [ # # ]: 0 : for( aIter = addon.begin(); aIter != addon.end(); ++aIter )
1408 : : {
1409 [ # # ]: 0 : PassMap::iterator aSearchIter = m_aContainer.find( aIter->first );
1410 [ # # ]: 0 : if( aSearchIter != m_aContainer.end() )
1411 [ # # ]: 0 : for( list< NamePassRecord >::iterator aNPIter = aIter->second.begin(); aNPIter != aIter->second.end(); ++aNPIter )
1412 [ # # ]: 0 : UpdateVector( aSearchIter->first, aSearchIter->second, *aNPIter, sal_False );
1413 : : else
1414 [ # # ][ # # ]: 0 : m_aContainer.insert( PairUrlRecord( aIter->first, aIter->second ) );
1415 [ # # ]: 0 : }
1416 : 0 : }
1417 : :
1418 : : //-------------------------------------------------------------------------
1419 : :
1420 : 0 : ::rtl::OUString SAL_CALL PasswordContainer::getImplementationName( ) throw(uno::RuntimeException)
1421 : : {
1422 : 0 : return impl_getStaticImplementationName();
1423 : : }
1424 : :
1425 : : //-------------------------------------------------------------------------
1426 : :
1427 : 0 : sal_Bool SAL_CALL PasswordContainer::supportsService( const ::rtl::OUString& ServiceName ) throw(uno::RuntimeException)
1428 : : {
1429 [ # # ]: 0 : if ( ServiceName.compareToAscii("com.sun.star.task.PasswordContainer") == 0 )
1430 : 0 : return sal_True;
1431 : : else
1432 : 0 : return sal_False;
1433 : : }
1434 : :
1435 : : //-------------------------------------------------------------------------
1436 : :
1437 : 0 : Sequence< ::rtl::OUString > SAL_CALL PasswordContainer::getSupportedServiceNames( ) throw(uno::RuntimeException)
1438 : : {
1439 : 0 : return impl_getStaticSupportedServiceNames();
1440 : : }
1441 : :
1442 : : //-------------------------------------------------------------------------
1443 : :
1444 : 2 : Sequence< ::rtl::OUString > SAL_CALL PasswordContainer::impl_getStaticSupportedServiceNames( ) throw(uno::RuntimeException)
1445 : : {
1446 : 2 : Sequence< ::rtl::OUString > aRet(1);
1447 [ + - ]: 2 : *aRet.getArray() = ::rtl::OUString("com.sun.star.task.PasswordContainer");
1448 : 2 : return aRet;
1449 : : }
1450 : :
1451 : : //-------------------------------------------------------------------------
1452 : :
1453 : 4 : ::rtl::OUString SAL_CALL PasswordContainer::impl_getStaticImplementationName() throw(uno::RuntimeException)
1454 : : {
1455 : 4 : return ::rtl::OUString("stardiv.svl.PasswordContainer");
1456 : : }
1457 : :
1458 : : //-------------------------------------------------------------------------
1459 : :
1460 : 2 : Reference< XInterface > SAL_CALL PasswordContainer::impl_createInstance( const Reference< XMultiServiceFactory >& xServiceManager ) throw( RuntimeException )
1461 : : {
1462 [ + - ]: 2 : return Reference< XInterface >( *new PasswordContainer( xServiceManager ) );
1463 : : }
1464 : :
1465 : : //-------------------------------------------------------------------------
1466 : :
1467 : 2 : Reference< XSingleServiceFactory > SAL_CALL PasswordContainer::impl_createFactory( const Reference< XMultiServiceFactory >& ServiceManager ) throw(RuntimeException)
1468 : : {
1469 : : Reference< XSingleServiceFactory > xReturn( ::cppu::createOneInstanceFactory( ServiceManager,
1470 : : PasswordContainer::impl_getStaticImplementationName(),
1471 : : PasswordContainer::impl_createInstance,
1472 [ + - ][ + - ]: 2 : PasswordContainer::impl_getStaticSupportedServiceNames()));
[ + - ]
1473 : 2 : return xReturn ;
1474 : :
1475 : : }
1476 : :
1477 : : //-------------------------------------------------------------------------
1478 : : //-------------------------------------------------------------------------
1479 : :
1480 : 4 : MasterPasswordRequest_Impl::MasterPasswordRequest_Impl( PasswordRequestMode Mode )
1481 : : {
1482 [ + - ]: 4 : MasterPasswordRequest aRequest;
1483 : :
1484 : 4 : aRequest.Classification = InteractionClassification_ERROR;
1485 : 4 : aRequest.Mode = Mode;
1486 : :
1487 [ + - ][ + - ]: 4 : setRequest( makeAny( aRequest ) );
1488 : :
1489 : : // Fill continuations...
1490 [ + - ]: 4 : Sequence< RememberAuthentication > aRememberModes( 1 );
1491 [ + - ]: 4 : aRememberModes[ 0 ] = RememberAuthentication_NO;
1492 : :
1493 : : m_xAuthSupplier
1494 : : = new ::ucbhelper::InteractionSupplyAuthentication(
1495 : : this,
1496 : : sal_False, // bCanSetRealm
1497 : : sal_False, // bCanSetUserName
1498 : : sal_True, // bCanSetPassword
1499 : : sal_False, // bCanSetAccount
1500 : : aRememberModes, // rRememberPasswordModes
1501 : : RememberAuthentication_NO, // eDefaultRememberPasswordMode
1502 : : aRememberModes, // rRememberAccountModes
1503 : : RememberAuthentication_NO, // eDefaultRememberAccountMode
1504 : : sal_False, // bCanUseSystemCredentials
1505 : : sal_False // bDefaultUseSystemCredentials
1506 [ + - ][ + - ]: 4 : );
1507 : :
1508 : : Sequence<
1509 [ + - ]: 4 : Reference< XInteractionContinuation > > aContinuations( 3 );
1510 [ + - ][ + - ]: 4 : aContinuations[ 0 ] = new ::ucbhelper::InteractionAbort( this );
[ + - ][ + - ]
1511 [ + - ][ + - ]: 4 : aContinuations[ 1 ] = new ::ucbhelper::InteractionRetry( this );
[ + - ][ + - ]
1512 [ + - ][ + - ]: 4 : aContinuations[ 2 ] = m_xAuthSupplier.get();
[ + - ]
1513 : :
1514 [ + - ][ + - ]: 4 : setContinuations( aContinuations );
[ + - ][ + - ]
1515 : 4 : }
1516 : :
1517 : : //-------------------------------------------------------------------------
1518 : : //-------------------------------------------------------------------------
1519 : :
1520 : : extern "C"
1521 : : {
1522 : 2 : SAL_DLLPUBLIC_EXPORT void * SAL_CALL passwordcontainer_component_getFactory (
1523 : : const sal_Char * pImplementationName,
1524 : : SAL_UNUSED_PARAMETER void * pServiceManager,
1525 : : SAL_UNUSED_PARAMETER void * /* pRegistryKey */)
1526 : : {
1527 : 2 : void * pResult = 0;
1528 [ + - ]: 2 : if (pServiceManager)
1529 : : {
1530 : 2 : Reference< XSingleServiceFactory > xFactory;
1531 [ + - ][ + - ]: 2 : if (PasswordContainer::impl_getStaticImplementationName().compareToAscii (pImplementationName) == 0)
1532 : : {
1533 : : xFactory = PasswordContainer::impl_createFactory (
1534 [ + - ][ + - ]: 2 : reinterpret_cast< XMultiServiceFactory* >(pServiceManager));
[ + - ]
1535 : : }
1536 [ + - ]: 2 : if (xFactory.is())
1537 : : {
1538 [ + - ]: 2 : xFactory->acquire();
1539 [ + - ]: 2 : pResult = xFactory.get();
1540 : 2 : }
1541 : : }
1542 : 2 : return pResult;
1543 : : }
1544 : :
1545 : : } // extern "C"
1546 : :
1547 : : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|