|
1 /* |
|
2 * Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). |
|
3 * All rights reserved. |
|
4 * This component and the accompanying materials are made available |
|
5 * under the terms of "Eclipse Public License v1.0"" |
|
6 * which accompanies this distribution, and is available |
|
7 * at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
8 * |
|
9 * Initial Contributors: |
|
10 * Nokia Corporation - initial contribution. |
|
11 * |
|
12 * Contributors: |
|
13 * |
|
14 * Description: CMMCScBkupReadDataTransferRequestBase implementation |
|
15 * |
|
16 * |
|
17 */ |
|
18 |
|
19 #include "CMMCScBkupTransferReadRequest.h" |
|
20 |
|
21 // User includes |
|
22 #include "MMCScBkupLogger.h" |
|
23 #include "MMMCScBkupDriver.h" |
|
24 #include "CMMCScBkupArchive.h" |
|
25 #include "MMMCScBkupArchiveDataInterface.h" |
|
26 #include "MMMCScBkupProgressObserver.h" |
|
27 #include <pathinfo.h> |
|
28 |
|
29 // Constants |
|
30 const TBool KMMCScBkupDontUpdateOpSizes = EFalse; |
|
31 |
|
32 |
|
33 |
|
34 // ========================= MEMBER FUNCTIONS ================================ |
|
35 |
|
36 // --------------------------------------------------------------------------- |
|
37 // CMMCScBkupReadDataTransferRequestBase::CMMCScBkupReadDataTransferRequestBase() |
|
38 // |
|
39 // C++ constructor. |
|
40 // --------------------------------------------------------------------------- |
|
41 CMMCScBkupReadDataTransferRequestBase::CMMCScBkupReadDataTransferRequestBase( |
|
42 MMMCScBkupDriver& aDriver, |
|
43 TMMCScBkupOwnerDataType aElementType, |
|
44 TInt aChunkSize, |
|
45 TInt aPriority ) |
|
46 : CMMCScBkupTransferRequestBase( aDriver, aElementType, KMMCScBkupDontUpdateOpSizes, aPriority ), |
|
47 iReadChunkSize( aChunkSize ), |
|
48 iCurrentIndex( -1 ) |
|
49 { |
|
50 } |
|
51 |
|
52 |
|
53 // --------------------------------------------------------------------------- |
|
54 // CMMCScBkupReadDataTransferRequestBase::~CMMCScBkupReadDataTransferRequestBase() |
|
55 // |
|
56 // Destructor. |
|
57 // --------------------------------------------------------------------------- |
|
58 CMMCScBkupReadDataTransferRequestBase::~CMMCScBkupReadDataTransferRequestBase() |
|
59 { |
|
60 delete iTransferType; |
|
61 delete iTemporaryTransferSink; |
|
62 } |
|
63 |
|
64 |
|
65 // --------------------------------------------------------------------------- |
|
66 // CMMCScBkupReadDataTransferRequestBase::RequestL() |
|
67 // |
|
68 // |
|
69 // --------------------------------------------------------------------------- |
|
70 void CMMCScBkupReadDataTransferRequestBase::RequestL( CMMCScBkupDataOwnerInfo& aOwner, TRequestStatus& aObserver, const RArray<TMMCScBkupArchiveDriveAndVector>& aEntries ) |
|
71 { |
|
72 #ifdef __MMCSCBKUPLOGGING_ENABLED__ |
|
73 if ( ElementType() == EMMCScBkupOwnerDataTypeJavaData ) |
|
74 { |
|
75 HBufC* hash = MMCScBkupSBEUtils::JavaHashFromGenericLC( aOwner.Owner().Identifier() ); |
|
76 __LOG2("CMMCScBkupReadDataTransferRequestBase::RequestL() - START - reading data from SBE for JavaHash: %S, ElementType: %S", hash, &MMCScBkupLogger::DataType( ElementType() )); |
|
77 CleanupStack::PopAndDestroy( hash ); |
|
78 } |
|
79 else |
|
80 { |
|
81 __LOG2("CMMCScBkupReadDataTransferRequestBase::RequestL() - START - reading data from SBE for DO: 0x%08x, ElementType: %S", aOwner.SecureId().iId, &MMCScBkupLogger::DataType( ElementType() )); |
|
82 } |
|
83 #endif |
|
84 |
|
85 CMMCScBkupTransferRequestBase::RequestL( aOwner, aObserver ); |
|
86 // |
|
87 if ( !iTemporaryTransferSink ) |
|
88 { |
|
89 iTemporaryTransferSink = HBufC8::NewL( iReadChunkSize ); |
|
90 } |
|
91 // |
|
92 iEntries = &aEntries; |
|
93 iCurrentIndex = -1; // Increased by one in PrepareForNextEntry |
|
94 // |
|
95 TState nextState = EProcessData; |
|
96 const TBool entryAvailable = PrepareForNextEntry(); |
|
97 if ( !entryAvailable ) |
|
98 { |
|
99 nextState = EFinished; |
|
100 } |
|
101 // |
|
102 SetState( nextState ); |
|
103 CompleteSelf(); |
|
104 __LOG1("CMMCScBkupReadDataTransferRequestBase::RequestL() - END - nextState: %d", nextState); |
|
105 } |
|
106 |
|
107 |
|
108 // --------------------------------------------------------------------------- |
|
109 // CMMCScBkupReadDataTransferRequestBase::ProcessChunkOfDataL() |
|
110 // |
|
111 // |
|
112 // --------------------------------------------------------------------------- |
|
113 TBool CMMCScBkupReadDataTransferRequestBase::ProcessChunkOfDataL() |
|
114 { |
|
115 __ASSERT_ALWAYS( iCurrentIndex >= 0, User::Invariant() ); |
|
116 |
|
117 TBool callAgain = EFalse; |
|
118 |
|
119 // Do we need to move to the next entry? |
|
120 TBool entryAvailable = ( iCurrentIndex < iEntries->Count() ); |
|
121 if ( entryAvailable ) |
|
122 { |
|
123 // At least one more entry left to process.. but have we finished |
|
124 // the current entry? If we've read all the data, then the |
|
125 // answer is yes... |
|
126 const TMMCScBkupArchiveDriveAndVector& entry = (*iEntries)[ iCurrentIndex ]; |
|
127 const TInt endOffset = entry.iVector.EndOffset(); |
|
128 |
|
129 #ifdef __MMCSCBKUPLOGGING_ENABLED__ |
|
130 if ( ElementType() == EMMCScBkupOwnerDataTypeJavaData ) |
|
131 { |
|
132 HBufC* hash = MMCScBkupSBEUtils::JavaHashFromGenericLC( DataOwner().Owner().Identifier() ); |
|
133 __LOG6("CMMCScBkupReadDataTransferRequestBase::ProcessChunkOfDataL() - START - JavaHash: %S, ElementType: %S, offset: %8d, length: %8d, endOffset: %8d, drive: %c:", hash, &MMCScBkupLogger::DataType( ElementType() ), entry.iVector.Offset(), entry.iVector.Length(), endOffset, entry.iDrive + 'A' ); |
|
134 CleanupStack::PopAndDestroy( hash ); |
|
135 } |
|
136 else |
|
137 { |
|
138 __LOG6("CMMCScBkupReadDataTransferRequestBase::ProcessChunkOfDataL() - START - DO: 0x%08x, ElementType: %S, offset: %8d, length: %8d, endOffset: %8d, drive: %c:", DataOwner().SecureId().iId, &MMCScBkupLogger::DataType( ElementType() ), entry.iVector.Offset(), entry.iVector.Length(), endOffset, entry.iDrive + 'A' ); |
|
139 } |
|
140 #endif |
|
141 |
|
142 // Check bounds |
|
143 if ( CurrentOffset() < 0 || CurrentOffset() > endOffset ) |
|
144 { |
|
145 ASSERT( EFalse ); |
|
146 User::Leave( KErrCorrupt ); |
|
147 } |
|
148 // |
|
149 if ( iCurrentOffset == endOffset ) |
|
150 { |
|
151 // We're done with this entry - move to the next |
|
152 entryAvailable = PrepareForNextEntry(); |
|
153 } |
|
154 } |
|
155 // |
|
156 if ( entryAvailable ) |
|
157 { |
|
158 // We need to read more archive data in order to transfer this |
|
159 // entry to the SBE |
|
160 callAgain = DoProcessChunkOfDataL(); |
|
161 } |
|
162 else |
|
163 { |
|
164 // No more left to process - we're finished! |
|
165 SetState( EFinished ); |
|
166 CompleteSelf(); |
|
167 } |
|
168 // |
|
169 return callAgain; |
|
170 } |
|
171 |
|
172 |
|
173 // --------------------------------------------------------------------------- |
|
174 // CMMCScBkupReadDataTransferRequestBase::PrepareDataTransferL() |
|
175 // |
|
176 // |
|
177 // --------------------------------------------------------------------------- |
|
178 void CMMCScBkupReadDataTransferRequestBase::PrepareDataTransferL() |
|
179 { |
|
180 __ASSERT_ALWAYS(iTransferChunkPointer != NULL, User::Invariant()); |
|
181 const CSBGenericDataType& generic = DataOwner().Owner().Identifier(); |
|
182 |
|
183 // Prepare the transfer type with a virtual function call... |
|
184 CSBGenericTransferType* transferType = PrepareTransferTypeL( generic, CurrentDrive(), |
|
185 DataOwner().Version()); |
|
186 delete iTransferType; |
|
187 iTransferType = transferType; |
|
188 |
|
189 #ifdef __MMCSCBKUPLOGGING_ENABLED__ |
|
190 TInt lengthOfDataReadyForTransfer = 0; |
|
191 if ( iTransferChunkPointer != NULL ) |
|
192 { |
|
193 lengthOfDataReadyForTransfer = iTransferChunkPointer->Length(); |
|
194 } |
|
195 |
|
196 if ( iTransferType->DerivedTypeL() == EJavaTransferDerivedType ) |
|
197 { |
|
198 HBufC* hash = MMCScBkupSBEUtils::JavaHashFromGenericLC( DataOwner().Owner().Identifier() ); |
|
199 __LOG5("CMMCScBkupReadDataTransferRequestBase::PrepareDataTransferL() - supplying %d bytes of data for has: %S, drive: %c, iTransferChunkPointer addr: 0x%08x, iTransferChunkPointer length: %d", lengthOfDataReadyForTransfer, hash, 'A' + CurrentDrive(), iTransferChunkPointer->Ptr(), iTransferChunkPointer->Length() ); |
|
200 CleanupStack::PopAndDestroy( hash ); |
|
201 } |
|
202 else |
|
203 { |
|
204 const TSecureId sid = DataOwner().SecureId(); |
|
205 __LOG5("CMMCScBkupReadDataTransferRequestBase::PrepareDataTransferL() - supplying %d bytes of data for sid: 0x%08x, drive: %c, iTransferChunkPointer addr: 0x%08x, iTransferChunkPointer length: %d", lengthOfDataReadyForTransfer, sid.iId, 'A' + CurrentDrive(), iTransferChunkPointer->Ptr(), iTransferChunkPointer->Length() ); |
|
206 } |
|
207 #endif |
|
208 |
|
209 // |
|
210 Driver().DrvSecureBackupClient().SupplyDataL( *iTransferType, iFinishedSupplyingData, iStatus ); |
|
211 SetActive(); |
|
212 |
|
213 // Reset |
|
214 ResetDataTransferCounter(); |
|
215 iTransferChunkPointer = NULL; // Address is retrieved from global chunk in DoProcessChunkOfDataL |
|
216 |
|
217 __LOG("CMMCScBkupReadDataTransferRequestBase::PrepareDataTransferL() - data transmitted, waiting for request completion..."); |
|
218 |
|
219 // When the SBE informs us that it has read the data, we'll need to send it the next |
|
220 // chunk. |
|
221 SetState( EProcessData ); |
|
222 } |
|
223 |
|
224 |
|
225 // --------------------------------------------------------------------------- |
|
226 // CMMCScBkupReadDataTransferRequestBase::ReadChunkL() |
|
227 // |
|
228 // |
|
229 // --------------------------------------------------------------------------- |
|
230 void CMMCScBkupReadDataTransferRequestBase::ReadChunkL( TDes8& aSink, TInt aLength ) |
|
231 { |
|
232 const TInt endOffset = CurrentReadInfo().EndOffset(); |
|
233 __LOG4("CMMCScBkupReadDataTransferRequestBase::ReadChunkL() - START - aLength: %d, endOffset: %d, iCurrentOffset: %d, sinkLength: %d", aLength, endOffset, iCurrentOffset, aSink.Length()); |
|
234 // |
|
235 if ( iCurrentOffset >= 0 && iCurrentOffset <= endOffset ) |
|
236 { |
|
237 if ( aLength > 0 ) |
|
238 { |
|
239 MMMCScBkupArchiveDataInterface& archiveDataInterface = Driver().DrvADI(); |
|
240 |
|
241 // We read based upon the current offset and the specified length |
|
242 TPtr8 sink( iTemporaryTransferSink->Des() ); |
|
243 const TMMCScBkupArchiveVector readRequest( iCurrentOffset, aLength ); |
|
244 const TMMCScBkupArchiveVector& readResult = archiveDataInterface.ADIReadL( sink, readRequest ); |
|
245 __LOG2("CMMCScBkupReadDataTransferRequestBase::ReadChunkL() - read result - offset: %d, length: %d", readResult.Offset(), readResult.Length()); |
|
246 |
|
247 // Update offset |
|
248 iCurrentOffset += readResult.Length(); |
|
249 aSink.Append( sink ); |
|
250 __LOG2("CMMCScBkupReadDataTransferRequestBase::ReadChunkL() - new offset (iCurrentOffset): %d, sink Length: %d", iCurrentOffset, aSink.Length()); |
|
251 |
|
252 #ifdef DEBUGGING_DATA_TRANSFER |
|
253 TRAP_IGNORE( DumpTransferDataL( archiveDataInterface.ADIFsSession(), sink) ); |
|
254 #endif |
|
255 |
|
256 if ( iCurrentOffset > CurrentReadInfo().EndOffset() ) |
|
257 { |
|
258 __LOG("CMMCScBkupReadDataTransferRequestBase::ReadChunkL() - Fatal Error - read went beyond archive entry boundary!"); |
|
259 ASSERT( EFalse ); |
|
260 User::Leave( KErrCorrupt ); |
|
261 } |
|
262 else |
|
263 { |
|
264 __LOG("CMMCScBkupReadDataTransferRequestBase::ReadChunkL() - read was okay - updating stats & reporting progress..."); |
|
265 |
|
266 // We managed to read the data okay, so let's update our stats |
|
267 DataTransferred( readResult.Length() ); |
|
268 |
|
269 // ... and also update progress |
|
270 Driver().DrvProgressHandler().MMCScBkupHandleProgress( readResult.Length() ); |
|
271 } |
|
272 } |
|
273 } |
|
274 else |
|
275 { |
|
276 __LOG("CMMCScBkupReadDataTransferRequestBase::ReadChunkL() - Fatal Error - current offset out of bounds!"); |
|
277 ASSERT( EFalse ); |
|
278 User::Leave( KErrCorrupt ); |
|
279 } |
|
280 |
|
281 __LOG("CMMCScBkupReadDataTransferRequestBase::ReadChunkL() - END"); |
|
282 } |
|
283 |
|
284 |
|
285 // --------------------------------------------------------------------------- |
|
286 // CMMCScBkupReadDataTransferRequestBase::DoProcessChunkOfDataL() |
|
287 // |
|
288 // |
|
289 // --------------------------------------------------------------------------- |
|
290 TBool CMMCScBkupReadDataTransferRequestBase::DoProcessChunkOfDataL() |
|
291 { |
|
292 MMMCScBkupDriver& driver = Driver(); |
|
293 const TInt startingOffset = CurrentOffset(); |
|
294 const TInt finalOffset = CurrentReadInfo().EndOffset(); |
|
295 |
|
296 // Calculate how much data is remaining |
|
297 const TInt amountOfDataStillToBeRead = finalOffset - startingOffset; |
|
298 |
|
299 __LOG4("CMMCScBkupReadDataTransferRequestBase::DoProcessChunkOfDataL() - START - startingOffset: 0x%08x, finalOffset: 0x%08x, amountToBeRead: %8d, iFinishedSupplyingData: %d", |
|
300 startingOffset, finalOffset, amountOfDataStillToBeRead, iFinishedSupplyingData); |
|
301 |
|
302 // Get a handle to the received data - but only if we don't already |
|
303 // have a handle to it! Calling this method resets whatever is already |
|
304 // in the transfer chunk - hence we must only call it once (at the beginning |
|
305 // of a multi-chunked transfer) |
|
306 if ( iTransferChunkPointer == NULL ) |
|
307 { |
|
308 iTransferChunkPointer = &driver.DrvSecureBackupClient().TransferDataAddressL(); |
|
309 } |
|
310 |
|
311 // How much space is available? |
|
312 const TInt spaceAvailable = iTransferChunkPointer->MaxLength() - iTransferChunkPointer->Length(); |
|
313 const TInt amountToRead = Min( spaceAvailable, Min( iReadChunkSize, amountOfDataStillToBeRead ) ); |
|
314 __LOG2("CMMCScBkupReadDataTransferRequestBase::DoProcessChunkOfDataL() - xfer space available: %8d, amountToRead: %8d", spaceAvailable, amountToRead); |
|
315 |
|
316 // Do the read |
|
317 ReadChunkL( *iTransferChunkPointer, amountToRead ); |
|
318 |
|
319 // Was this the last time we needed to perform a read? |
|
320 const TBool lastReadFromArchive = ( CurrentOffset() == finalOffset ); |
|
321 __LOG1("CMMCScBkupReadDataTransferRequestBase::DoProcessChunkOfDataL() - read data okay - lastReadFromArchive: %d", lastReadFromArchive); |
|
322 |
|
323 // Check to see if the data sink chunk is full. If so then we need to let |
|
324 // the SBE process what we've prepared so far, then we'll fill it with more |
|
325 // data. |
|
326 iFinishedSupplyingData = lastReadFromArchive; |
|
327 TBool moreToBeRead = !lastReadFromArchive; |
|
328 if ( !iFinishedSupplyingData && iTransferChunkPointer->Length() == iTransferChunkPointer->MaxLength() ) |
|
329 { |
|
330 // Also cope with the boundary condition that the sink is full |
|
331 // but we've also just given it the last byte anyway. In which case, |
|
332 // we don't need to request a repeat transfer. This is actually |
|
333 // all the data in one go. |
|
334 moreToBeRead = EFalse; |
|
335 } |
|
336 // |
|
337 __LOG1("CMMCScBkupReadDataTransferRequestBase::DoProcessChunkOfDataL() - END - more to read: %d", moreToBeRead); |
|
338 return moreToBeRead; |
|
339 } |
|
340 |
|
341 |
|
342 // --------------------------------------------------------------------------- |
|
343 // CMMCScBkupReadDataTransferRequestBase::PrepareForNextEntry() |
|
344 // |
|
345 // |
|
346 // --------------------------------------------------------------------------- |
|
347 TBool CMMCScBkupReadDataTransferRequestBase::PrepareForNextEntry() |
|
348 { |
|
349 TBool anotherEntryAvailable = EFalse; |
|
350 |
|
351 // Update our starting offset |
|
352 iFinishedSupplyingData = EFalse; |
|
353 iCurrentOffset = -1; |
|
354 // |
|
355 if ( ++iCurrentIndex < iEntries->Count() ) |
|
356 { |
|
357 const TMMCScBkupArchiveVector& currentReadInfo = CurrentReadInfo(); |
|
358 iCurrentOffset = currentReadInfo.Offset(); |
|
359 |
|
360 __LOG3("CMMCScBkupReadDataTransferRequestBase::PrepareForNextEntry() - offset: %6d, length: %6d, drive: %c:", currentReadInfo.Offset(), currentReadInfo.Length(), 'A' + CurrentDrive() ); |
|
361 |
|
362 anotherEntryAvailable = ETrue; |
|
363 } |
|
364 // |
|
365 return anotherEntryAvailable; |
|
366 } |
|
367 |
|
368 |
|
369 // --------------------------------------------------------------------------- |
|
370 // CMMCScBkupReadDataTransferRequestBase::CurrentDrive() |
|
371 // |
|
372 // |
|
373 // --------------------------------------------------------------------------- |
|
374 TDriveNumber CMMCScBkupReadDataTransferRequestBase::CurrentDrive() const |
|
375 { |
|
376 return CurrentEntry().iDrive; |
|
377 } |
|
378 |
|
379 |
|
380 // --------------------------------------------------------------------------- |
|
381 // CMMCScBkupReadDataTransferRequestBase::CurrentReadInfo() |
|
382 // |
|
383 // |
|
384 // --------------------------------------------------------------------------- |
|
385 const TMMCScBkupArchiveVector& CMMCScBkupReadDataTransferRequestBase::CurrentReadInfo() const |
|
386 { |
|
387 return CurrentEntry().iVector; |
|
388 } |
|
389 |
|
390 |
|
391 // --------------------------------------------------------------------------- |
|
392 // CMMCScBkupReadDataTransferRequestBase::CurrentEntry() |
|
393 // |
|
394 // |
|
395 // --------------------------------------------------------------------------- |
|
396 const TMMCScBkupArchiveDriveAndVector& CMMCScBkupReadDataTransferRequestBase::CurrentEntry() const |
|
397 { |
|
398 __ASSERT_ALWAYS( iCurrentIndex >= 0 && iCurrentIndex < iEntries->Count(), User::Invariant() ); |
|
399 |
|
400 // Get the next entry |
|
401 const TMMCScBkupArchiveDriveAndVector& entry = (*iEntries)[ iCurrentIndex ]; |
|
402 return entry; |
|
403 } |
|
404 |
|
405 |
|
406 // --------------------------------------------------------------------------- |
|
407 // CMMCScBkupReadDataTransferRequestBase::RunError() |
|
408 // |
|
409 // |
|
410 // --------------------------------------------------------------------------- |
|
411 TInt CMMCScBkupReadDataTransferRequestBase::RunError( TInt aError ) |
|
412 { |
|
413 #if defined(__MMCSCBKUPLOGGING_ENABLED__) |
|
414 const TSecureId sid = DataOwner().SecureId(); |
|
415 __LOGFILE3("CMMCScBkupReadDataTransferRequestBase::RunError() - **** - aError: %d, sid: 0x%08x, drive: %c", aError, sid.iId, 'A' + CurrentDrive() ); |
|
416 #endif |
|
417 |
|
418 TInt ret = KErrNone; |
|
419 |
|
420 if ( aError == KErrNotFound ) |
|
421 { |
|
422 // KErrNotFound is treated as non-fatal. |
|
423 const TBool entryAvailable = PrepareForNextEntry(); |
|
424 |
|
425 // Try the next entry (if any) |
|
426 TState nextState = EProcessData; |
|
427 if ( entryAvailable ) |
|
428 { |
|
429 __LOGFILE("CMMCScBkupReadDataTransferRequestBase::RunError() - **** - another drive available for same DO - trying the next drive..."); |
|
430 nextState = EProcessData; |
|
431 } |
|
432 else |
|
433 { |
|
434 // Done |
|
435 __LOGFILE("CMMCScBkupReadDataTransferRequestBase::RunError() - **** - no drives let for same DO..."); |
|
436 nextState = EFinished; |
|
437 } |
|
438 |
|
439 SetState( nextState ); |
|
440 CompleteSelf(); |
|
441 } |
|
442 else |
|
443 { |
|
444 // Everything else is fatal |
|
445 __LOGFILE1( "CMMCScBkupReadDataTransferRequestBase::RunError() - **** - FATAL ERROR (%d)", aError ); |
|
446 ret = CMMCScBkupTransferRequestBase::RunError( aError ); |
|
447 } |
|
448 // |
|
449 return ret; |
|
450 } |
|
451 |
|
452 |
|
453 // --------------------------------------------------------------------------- |
|
454 // CMMCScBkupReadDataTransferRequestBase::DumpTransferDataL() |
|
455 // |
|
456 // |
|
457 // --------------------------------------------------------------------------- |
|
458 #ifdef DEBUGGING_DATA_TRANSFER |
|
459 void CMMCScBkupReadDataTransferRequestBase::DumpTransferDataL( RFs& aFsSession, const TDesC8& aData ) const |
|
460 { |
|
461 TPtrC subDirectory( KNullDesC ); |
|
462 // |
|
463 switch( ElementType() ) |
|
464 { |
|
465 case EMMCScBkupOwnerDataTypeJavaData: |
|
466 subDirectory.Set(KMMCScBkupDataTransferDebuggingPathDataJava); |
|
467 break; |
|
468 case EMMCScBkupOwnerDataTypeSystemData: |
|
469 subDirectory.Set(KMMCScBkupDataTransferDebuggingPathDataSystem); |
|
470 break; |
|
471 case EMMCScBkupOwnerDataTypePassiveData: |
|
472 subDirectory.Set(KMMCScBkupDataTransferDebuggingPathDataPassive); |
|
473 break; |
|
474 case EMMCScBkupOwnerDataTypeActiveData: |
|
475 subDirectory.Set(KMMCScBkupDataTransferDebuggingPathDataActive); |
|
476 break; |
|
477 default: |
|
478 User::Leave( KErrNotSupported ); |
|
479 break; |
|
480 } |
|
481 // |
|
482 const TSecureId secureId = DataOwner().SecureId(); |
|
483 _LIT(KMMCScBkupFormatDes, "%S%S"); |
|
484 TFileName transferDumpFileName; |
|
485 const TDesC& path = PathInfo::MemoryCardRootPath(); |
|
486 transferDumpFileName.Format(KMMCScBkupFormatDes, &path, &KMMCScBkupDataTransferDebuggingPathRoot); |
|
487 |
|
488 transferDumpFileName.Append( subDirectory ); |
|
489 transferDumpFileName.Append( KMMCScBkupDataTransferDebuggingPathDataRestore ); |
|
490 transferDumpFileName.AppendFormat( KMMCScBkupDataTransferDebuggingFileName, secureId.iId, 'a' + CurrentDrive() ); |
|
491 // |
|
492 RFile64 file; |
|
493 TInt error = KErrNone; |
|
494 TEntry entry; |
|
495 if ( aFsSession.Entry( transferDumpFileName, entry ) == KErrNone ) |
|
496 { |
|
497 // Already exists - append data |
|
498 error = file.Open( aFsSession, transferDumpFileName, EFileWrite | EFileStream | EFileShareExclusive ); |
|
499 } |
|
500 else |
|
501 { |
|
502 entry.iSize = 0; |
|
503 error = file.Create( aFsSession, transferDumpFileName, EFileWrite | EFileStream | EFileShareExclusive ); |
|
504 } |
|
505 // |
|
506 User::LeaveIfError( error ); |
|
507 CleanupClosePushL( file ); |
|
508 error = file.Write( entry.iSize, aData ); |
|
509 CleanupStack::PopAndDestroy( &file ); |
|
510 } |
|
511 #endif |
|
512 |
|
513 |
|
514 |
|
515 |
|
516 |
|
517 |