1 // Copyright (c) 2000-2009 Nokia Corporation and/or its subsidiary(-ies). |
|
2 // All rights reserved. |
|
3 // This component and the accompanying materials are made available |
|
4 // under the terms of "Eclipse Public License v1.0" |
|
5 // which accompanies this distribution, and is available |
|
6 // at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
7 // |
|
8 // Initial Contributors: |
|
9 // Nokia Corporation - initial contribution. |
|
10 // |
|
11 // Contributors: |
|
12 // |
|
13 // Description: |
|
14 // |
|
15 |
|
16 #ifdef _DEBUG |
|
17 #undef _MSG_NO_LOGGING |
|
18 #endif |
|
19 |
|
20 #include <smutset.h> |
|
21 #include <txtrich.h> |
|
22 #include <smuthdr.h> |
|
23 #include <msventry.h> |
|
24 #include <msvuids.h> |
|
25 #include <mmlist.h> |
|
26 #include <smutsimparam.h> |
|
27 #include <biodb.h> |
|
28 #include <biouids.h> |
|
29 #include <csmsaccount.h> |
|
30 |
|
31 #include "SmssSimUtils.h" |
|
32 #include "SMSSPAN.H" |
|
33 |
|
34 //Logging constants |
|
35 |
|
36 #ifndef _MSG_NO_LOGGING |
|
37 _LIT(KDeleteFromSimLog, "DeleteFromSim.txt"); |
|
38 _LIT(KEnumerateSimLog, "EnumerateSim.txt"); |
|
39 _LIT(KCopyToSimLog, "CopyToSim.txt"); |
|
40 #endif |
|
41 |
|
42 //CopyToSim constants |
|
43 |
|
44 |
|
45 CSmsSimUtils* CSmsSimUtils::NewL(CMsvServerEntry& aServerEntry, RFs& aFs, TMsvId aSmsServiceId) |
|
46 { |
|
47 CSmsSimUtils* self = new (ELeave) CSmsSimUtils(aServerEntry, aFs, aSmsServiceId); |
|
48 CleanupStack::PushL(self); |
|
49 self->ConstructL(); |
|
50 CleanupStack::Pop(self); |
|
51 return self; |
|
52 } |
|
53 |
|
54 void CSmsSimUtils::ConstructL() |
|
55 { |
|
56 iSettings = CSmsSettings::NewL(); |
|
57 |
|
58 // load ECOM interface used to create SMS details and description values. |
|
59 iGetDetDesc = CSmsGetDetDescInterface::NewL(); |
|
60 } |
|
61 |
|
62 CSmsSimUtils::~CSmsSimUtils() |
|
63 { |
|
64 Cancel(); |
|
65 |
|
66 iWriteStream.Close(); |
|
67 iReadStream.Close(); |
|
68 |
|
69 iSocket.Close(); |
|
70 iSocketServ.Close(); |
|
71 |
|
72 delete iSelection; |
|
73 delete iCompletedSelection; |
|
74 |
|
75 delete iHeader; |
|
76 delete iBody; |
|
77 delete iCharFormat; |
|
78 delete iParaFormat; |
|
79 |
|
80 delete iBioDb; |
|
81 delete iSettings; |
|
82 |
|
83 delete iGetDetDesc; |
|
84 REComSession::FinalClose(); |
|
85 } |
|
86 |
|
87 void CSmsSimUtils::ReadSimParamsL(TRequestStatus& aStatus) |
|
88 /** |
|
89 Reads the SMS parameters from the SIM |
|
90 |
|
91 @since 7.0 |
|
92 @param aStatus Indicates the completion status of a request made to |
|
93 a service provider. |
|
94 @pre None |
|
95 @post Starts the reading async operation. |
|
96 */ |
|
97 { |
|
98 SMSSLOG(FLogFormat(_L8("Reading SMS SIM Parameters"))); |
|
99 |
|
100 Queue(aStatus); |
|
101 |
|
102 iProgress = TSmsProgress(); |
|
103 iProgress.iType = TSmsProgress::ESmsProgressTypeReadSimParams; |
|
104 |
|
105 ConnectL(); |
|
106 |
|
107 iSocket.Ioctl(KIoctlReadSmsParams, iStatus, NULL, KSolSmsProv); |
|
108 |
|
109 SetActive(); |
|
110 iReadingSimParams = ETrue; |
|
111 } |
|
112 |
|
113 void CSmsSimUtils::WriteSimParamsL(TRequestStatus& aStatus) |
|
114 /** |
|
115 Writes the SMS parameters to the SIM |
|
116 |
|
117 @since 7.0 |
|
118 @param aStatus |
|
119 @pre The parameters are stored in the message store. |
|
120 @post The parameters are retrived form the message store and the writing |
|
121 async operation is started. |
|
122 */ |
|
123 { |
|
124 SMSSLOG(FLogFormat(_L8("Writing SMS SIM Parameters"))); |
|
125 |
|
126 Queue(aStatus); |
|
127 |
|
128 iProgress = TSmsProgress(); |
|
129 iProgress.iType = TSmsProgress::ESmsProgressTypeWriteSimParams; |
|
130 |
|
131 CMobilePhoneSmspList* smspList = CMobilePhoneSmspList::NewL(); |
|
132 CleanupStack::PushL(smspList); |
|
133 |
|
134 User::LeaveIfError(iServerEntry.SetEntry(iSmsServiceId)); |
|
135 |
|
136 CMsvStore* store = iServerEntry.ReadStoreL(); |
|
137 CleanupStack::PushL(store); |
|
138 |
|
139 CSmsSimParamOperation::RestoreSimParamsL(*store, *smspList); |
|
140 |
|
141 TInt count = 0; |
|
142 count = smspList->Enumerate(); |
|
143 |
|
144 if (!count) |
|
145 User::Leave(KErrNotFound); |
|
146 |
|
147 ConnectL(); |
|
148 |
|
149 iWriteStream << *smspList; |
|
150 iWriteStream.CommitL(); |
|
151 |
|
152 CleanupStack::PopAndDestroy(2); //smspList, store |
|
153 User::LeaveIfError(iServerEntry.SetEntry(KMsvNullIndexEntryId)); |
|
154 |
|
155 iSocket.Ioctl(KIoctlWriteSmsParams, iStatus, NULL, KSolSmsProv); |
|
156 |
|
157 SetActive(); |
|
158 } |
|
159 |
|
160 void CSmsSimUtils::EnumerateL(const TDesC8& aParameter, TRequestStatus& aStatus) |
|
161 { |
|
162 SMSSLOG(FLogFormat(_L8("Enumerate messages in SIM [param=%d]"), aParameter.Length())); |
|
163 |
|
164 //Enumerate messages on the SIM. |
|
165 //First obtains a count of messages on the SIM. |
|
166 |
|
167 Queue(aStatus); |
|
168 iProgress = TSmsProgress(); |
|
169 iProgress.iType = TSmsProgress::ESmsProgressTypeEnumeratingPhoneStores; |
|
170 |
|
171 ConstructHeaderAndBodyL(); |
|
172 SetAndCleanEnumerateFolderL(aParameter); |
|
173 SMSSLOG(FLogFormat(_L8("\tUsing folder %d"), iProgress.iEnumerateFolder, aParameter.Length())); |
|
174 |
|
175 //Obtain a count of the messages on the SIM |
|
176 CountMessagesInPhoneStoresL(); |
|
177 } |
|
178 |
|
179 void CSmsSimUtils::SetAndCleanEnumerateFolderL(const TDesC8& aParameter) |
|
180 /** |
|
181 * |
|
182 * |
|
183 * @param aParameter Optionally contains the ID of the folder to store the phone store messages |
|
184 */ |
|
185 { |
|
186 iProgress.iEnumerateFolder = KErrNotFound; |
|
187 |
|
188 //Restore the iSimUtilsData. |
|
189 //This should be moved to a more general ContructL() if other functions other than EnumerateL() need to use this data |
|
190 RestoreSimUtilsDataL(); |
|
191 |
|
192 //Delete messages under the last folder used to store phone-side messages |
|
193 const TInt err = iServerEntry.SetEntry(iSimUtilsData.iLastEnumerateFolder); |
|
194 if (err == KErrNotFound) |
|
195 { |
|
196 iSimUtilsData.iLastEnumerateFolder = KErrNotFound; |
|
197 } |
|
198 else |
|
199 { |
|
200 //Clean the last folder used to store phone-side messages |
|
201 User::LeaveIfError(err); |
|
202 DeleteChildrenL(iSimUtilsData.iLastEnumerateFolder); |
|
203 } |
|
204 |
|
205 if (aParameter.Length() != 0) |
|
206 { |
|
207 //Use the TMsvId packaged in aParameter as the folder in which to store phone-side messages |
|
208 TPckgC<TMsvId> enumFolder(KErrNotFound); |
|
209 enumFolder.Set(aParameter); |
|
210 iProgress.iEnumerateFolder = enumFolder(); |
|
211 SMSSLOG(FLogFormat(_L8("\tAsked to use folder %d [last=%d]"), iProgress.iEnumerateFolder, iSimUtilsData.iLastEnumerateFolder)); |
|
212 |
|
213 switch (iProgress.iEnumerateFolder) |
|
214 { |
|
215 case KMsvRootIndexEntryId: |
|
216 case KMsvLocalServiceIndexEntryId: |
|
217 case KMsvGlobalInBoxIndexEntryId: |
|
218 case KMsvGlobalOutBoxIndexEntryId: |
|
219 case KMsvDraftEntryId: |
|
220 case KMsvSentEntryId: |
|
221 User::Leave(KErrArgument); //cannot store phone-side messages under a standard folder |
|
222 break; |
|
223 default: |
|
224 break; |
|
225 } |
|
226 |
|
227 //Check the folder exists and delete all its children |
|
228 User::LeaveIfError(iServerEntry.SetEntry(iProgress.iEnumerateFolder)); |
|
229 DeleteChildrenL(iProgress.iEnumerateFolder); |
|
230 } |
|
231 else |
|
232 { |
|
233 //else use the last folder used to store phone-side messages |
|
234 iProgress.iEnumerateFolder = iSimUtilsData.iLastEnumerateFolder; |
|
235 } |
|
236 |
|
237 if (iProgress.iEnumerateFolder == KErrNotFound) |
|
238 { |
|
239 //Create a new folder if last is not found AND aParameter,Length() == 0 |
|
240 //Note: CreateNewEnumerateFolderL() sets iSimUtilsData.iLastEnumerateFolder |
|
241 iProgress.iEnumerateFolder = CreateNewEnumerateFolderL(); |
|
242 } |
|
243 |
|
244 if (iProgress.iEnumerateFolder != iSimUtilsData.iLastEnumerateFolder) |
|
245 { |
|
246 //Delete the last enumerate folder if it is under the SMS service |
|
247 DeleteEnumerateFolderL(iSimUtilsData.iLastEnumerateFolder); |
|
248 |
|
249 //Store the enumerate folder for next time |
|
250 iSimUtilsData.iLastEnumerateFolder = iProgress.iEnumerateFolder; |
|
251 StoreSimUtilsDataL(); |
|
252 } |
|
253 } |
|
254 |
|
255 void CSmsSimUtils::DeleteEnumerateFolderL(TMsvId aId) |
|
256 /** |
|
257 * Deletes entry aId if its parent is iSmsServiceId |
|
258 */ |
|
259 { |
|
260 SMSSLOG(FLogFormat(_L8("\tAttempting to delete enumerate folder %d"), aId)); |
|
261 const TInt err = iServerEntry.SetEntry(aId); |
|
262 |
|
263 if (err != KErrNotFound) |
|
264 { |
|
265 User::LeaveIfError(aId); |
|
266 |
|
267 if (iServerEntry.Entry().Parent() == iSmsServiceId) |
|
268 { |
|
269 SMSSLOG(FLogFormat(_L8("\tDeleting enumerate folder %d"), aId)); |
|
270 User::LeaveIfError(iServerEntry.SetEntry(iSmsServiceId)); |
|
271 User::LeaveIfError(iServerEntry.DeleteEntry(aId)); |
|
272 } |
|
273 } |
|
274 } |
|
275 |
|
276 void CSmsSimUtils::DeleteChildrenL(TMsvId aId) |
|
277 /** |
|
278 * Deletes all messages under parent aId |
|
279 */ |
|
280 { |
|
281 SMSSLOG(FLogFormat(_L8("\tDeleting children from %d"), aId)); |
|
282 |
|
283 User::LeaveIfError(iServerEntry.SetEntry(aId)); |
|
284 |
|
285 TMsvSelectionOrdering order; |
|
286 order.SetShowInvisibleEntries(ETrue); |
|
287 iServerEntry.SetSort(order); |
|
288 |
|
289 CMsvEntrySelection* sel = new (ELeave) CMsvEntrySelection(); |
|
290 CleanupStack::PushL(sel); |
|
291 User::LeaveIfError(iServerEntry.GetChildren(*sel)); |
|
292 |
|
293 if (sel->Count() != 0) |
|
294 { |
|
295 User::LeaveIfError(iServerEntry.DeleteEntries(*sel)); |
|
296 } |
|
297 |
|
298 CleanupStack::PopAndDestroy(sel); |
|
299 } |
|
300 |
|
301 TMsvId CSmsSimUtils::CreateNewEnumerateFolderL() |
|
302 /** |
|
303 * Creates a new folder under the SMS service where phone-side messages will be stored |
|
304 * iSimUtilsData.iLastEnumerateFolder is set to the new folder's ID then stored against the SMS service |
|
305 * |
|
306 * @return the new folder's ID |
|
307 */ |
|
308 { |
|
309 SMSSLOG(FLogFormat(_L8("\tCreating new folder..."))); |
|
310 User::LeaveIfError(iServerEntry.SetEntry(iSmsServiceId)); |
|
311 |
|
312 TMsvEntry entry; |
|
313 |
|
314 //Create a new invisible folder under the local service |
|
315 entry.SetVisible(EFalse); |
|
316 entry.iType = KUidMsvFolderEntry; |
|
317 entry.iMtm = KUidMsgTypeSMS; |
|
318 entry.iServiceId = iSmsServiceId; |
|
319 User::LeaveIfError(iServerEntry.CreateEntry(entry)); |
|
320 iSimUtilsData.iLastEnumerateFolder = entry.Id(); |
|
321 |
|
322 TRAPD(err, StoreSimUtilsDataL()); |
|
323 |
|
324 if (err != KErrNone) |
|
325 { |
|
326 iServerEntry.DeleteEntry(entry.Id()); //remove the folder if StoreSimUtilsDataL() leaves |
|
327 User::Leave(err); |
|
328 } |
|
329 |
|
330 return iSimUtilsData.iLastEnumerateFolder; |
|
331 } |
|
332 |
|
333 void CSmsSimUtils::CountMessagesInPhoneStoresL() |
|
334 { |
|
335 SMSSLOG(FLogFormat(_L8("\tCounting Messages on SIM. Calling Ioctl KIoctlEnumerateSmsMessages"))); |
|
336 |
|
337 User::LeaveIfError(iServerEntry.SetEntry(KMsvNullIndexEntryId)); |
|
338 ConnectL(); |
|
339 CreateBioDbL(); |
|
340 iSocket.Ioctl(KIoctlEnumerateSmsMessages, iStatus, &iEnumerateCountBuf, KSolSmsProv); |
|
341 SetActive(); |
|
342 } |
|
343 |
|
344 void CSmsSimUtils::CreateBioDbL() |
|
345 { |
|
346 if (iBioDb == NULL) |
|
347 iBioDb = CBIODatabase::NewL(iFs); |
|
348 } |
|
349 |
|
350 TBool CSmsSimUtils::GetDefaultSendBearerL(TInt aBioType, TBioMsgIdType aBearer, TBioMsgId& rBioMsgId) const |
|
351 { |
|
352 TInt index = 0; |
|
353 TUid uid; |
|
354 uid.iUid = aBioType; |
|
355 TBool found = EFalse; |
|
356 TRAPD(ret,iBioDb->GetBioIndexWithMsgIDL(uid, index)); //leaves with KErrNotFound if aBioType does not exist in bdb |
|
357 if (ret==KErrNone) |
|
358 { |
|
359 const CArrayFix<TBioMsgId>* bioIDs = iBioDb->BIOEntryLC(index); |
|
360 const TInt count = bioIDs->Count(); |
|
361 |
|
362 for (TInt i = 0; !found && i < count; i++) //order important |
|
363 { |
|
364 rBioMsgId = bioIDs->At(i); |
|
365 found = (rBioMsgId.iType == aBearer); |
|
366 } |
|
367 |
|
368 CleanupStack::PopAndDestroy(); // bioIDs |
|
369 } |
|
370 else if (ret!=KErrNotFound) |
|
371 User::LeaveIfError(ret); |
|
372 return found; |
|
373 } |
|
374 |
|
375 TUid CSmsSimUtils::DecodeBioMessageL(TBioMsgId& rId) |
|
376 { |
|
377 TUid biomsguid=KNullUid; |
|
378 rId.iType=EBioMsgIdNbs; |
|
379 // Take text off front of message |
|
380 CSmsMessage& smsmessage=iHeader->Message(); |
|
381 const TInt length=smsmessage.Buffer().Length(); |
|
382 smsmessage.Buffer().Extract(rId.iText,0,length<KMaxBioIdText? length: KMaxBioIdText); |
|
383 TInt originator; |
|
384 TInt destination; |
|
385 // Has the message got application port addressing? |
|
386 if (smsmessage.SmsPDU().ApplicationPortAddressing(destination,originator)) |
|
387 { |
|
388 rId.iPort=STATIC_CAST(TUint16,destination); |
|
389 rId.iType=EBioMsgIdWap; |
|
390 // Is it WAP? |
|
391 if (iBioDb->IsBioMessageL(rId,biomsguid)==KErrNotFound) |
|
392 { |
|
393 rId.iType=EBioMsgIdWapSecure; |
|
394 // Is it WAP secure? |
|
395 if (iBioDb->IsBioMessageL(rId,biomsguid)==KErrNotFound) |
|
396 { |
|
397 rId.iType=EBioMsgIdWsp; |
|
398 // Is it WSP? |
|
399 if(iBioDb->IsBioMessageL(rId,biomsguid)==KErrNotFound) |
|
400 { |
|
401 rId.iType=EBioMsgIdWspSecure; |
|
402 // Is it WSP secure? |
|
403 iBioDb->IsBioMessageL(rId,biomsguid); |
|
404 } |
|
405 } |
|
406 } |
|
407 } |
|
408 else |
|
409 { |
|
410 // Is it an NBS style text message? |
|
411 TInt index=rId.iText.Locate('\r'); |
|
412 if (index==KErrNotFound) |
|
413 index=rId.iText.Locate('\n'); |
|
414 // Look for text match in BIO database |
|
415 if ((index>0) && (iBioDb->IsBioMessageL(EBioMsgIdNbs,rId.iText.Left(index),0,biomsguid) != KErrNotFound)) |
|
416 smsmessage.Buffer().DeleteL(0,index+1); // Remove BIO text |
|
417 } |
|
418 iHeader->SetBioMsgIdType(rId.iType); |
|
419 return biomsguid; |
|
420 } |
|
421 |
|
422 void CSmsSimUtils::EncodeBioMessageL() |
|
423 { |
|
424 CSmsMessage& smsmessage=iHeader->Message(); |
|
425 TBioMsgId bioMsgId; |
|
426 // Is it a BIO message? |
|
427 if (GetDefaultSendBearerL(iServerEntry.Entry().iBioType, iHeader->BioMsgIdType(), bioMsgId)) |
|
428 { |
|
429 switch (bioMsgId.iType) |
|
430 { |
|
431 case EBioMsgIdNbs: |
|
432 { |
|
433 // Put text on NBS message |
|
434 TBioMsgIdText text; |
|
435 CSmsBufferBase& buffer=smsmessage.Buffer(); |
|
436 TInt textlength=bioMsgId.iText.Length(); |
|
437 buffer.Extract(text,0,textlength<buffer.Length()? textlength: 0); |
|
438 if (bioMsgId.iText.CompareF(text)) |
|
439 { |
|
440 _LIT(KSmsNewLine,"\n"); |
|
441 buffer.InsertL(0,KSmsNewLine); |
|
442 buffer.InsertL(0,bioMsgId.iText); |
|
443 } |
|
444 break; |
|
445 } |
|
446 case EBioMsgIdWap: |
|
447 case EBioMsgIdWapSecure: |
|
448 case EBioMsgIdWsp: |
|
449 case EBioMsgIdWspSecure: |
|
450 { |
|
451 // Put port addressing on binary messages |
|
452 smsmessage.SmsPDU().SetApplicationPortAddressingL(ETrue,bioMsgId.iPort,bioMsgId.iPort,bioMsgId.iPort>255); |
|
453 smsmessage.SmsPDU().SetAlphabet(TSmsDataCodingScheme::ESmsAlphabet8Bit); |
|
454 } |
|
455 default: |
|
456 break; |
|
457 } |
|
458 } |
|
459 } |
|
460 |
|
461 void CSmsSimUtils::SetupMoveDeleteL(const CMsvEntrySelection& aSelection, TRequestStatus& aStatus) |
|
462 { |
|
463 __ASSERT_DEBUG(aSelection.Count(), Panic(KSmssPanicNoMessagesInSelection)); |
|
464 |
|
465 Queue(aStatus); |
|
466 iProgress = TSmsProgress(); |
|
467 |
|
468 if (iSelection != &aSelection) |
|
469 { |
|
470 delete iSelection; |
|
471 iSelection = NULL; |
|
472 iSelection = aSelection.CopyL(); |
|
473 iSelection->Delete(0); // Remove the SMS service entry id |
|
474 } |
|
475 |
|
476 iProgress.iMsgCount = iSelection->Count(); |
|
477 } |
|
478 |
|
479 void CSmsSimUtils::DeleteEachMessageFromPhoneStoreL() |
|
480 { |
|
481 iState = ESimUtilsStateOther; |
|
482 |
|
483 if (iProgress.iMsgDone < iProgress.iMsgCount) |
|
484 { |
|
485 ConstructHeaderAndBodyL(); |
|
486 |
|
487 const TMsvId id = iSelection->At(iProgress.iMsgDone); |
|
488 const TInt err = iServerEntry.SetEntry(id); |
|
489 |
|
490 if (err == KErrNone) |
|
491 { |
|
492 CMsvStore* store = iServerEntry.ReadStoreL(); |
|
493 CleanupStack::PushL(store); |
|
494 |
|
495 store->RestoreBodyTextL(*iBody); |
|
496 iHeader->RestoreL(*store); |
|
497 CleanupStack::PopAndDestroy(); //store |
|
498 |
|
499 iProgress.iError = KErrNone; |
|
500 |
|
501 SMSSLOG(FLogMessage(iServerEntry.Entry(), iHeader->Message(), iHeader->BioMsgIdType(), KDeleteFromSimLog)); |
|
502 SMSSLOG(FLogFormat(_L8("\tDeleting %d from SIM (%d/%d)"), id, iProgress.iMsgDone+1, iProgress.iMsgCount)); |
|
503 |
|
504 iWriteStream << iHeader->Message(); |
|
505 iWriteStream.CommitL(); |
|
506 iSocket.Ioctl(KIoctlDeleteSmsMessage, iStatus, NULL, KSolSmsProv); |
|
507 iState = ESimUtilsDeleteEachMessage; |
|
508 } |
|
509 else |
|
510 { |
|
511 SMSSLOG(FLogFormat(_L8("\tIgnoring %d, Error=%d"), id, err)); |
|
512 RequestComplete(&iStatus, KErrNone); |
|
513 } |
|
514 |
|
515 SetActive(); |
|
516 iProgress.iMsgDone++; |
|
517 User::LeaveIfError(iServerEntry.SetEntry(KMsvNullIndexEntryId)); |
|
518 } |
|
519 else |
|
520 { |
|
521 iState = ESimUtilsDeletedLastMessage; |
|
522 } |
|
523 } |
|
524 |
|
525 void CSmsSimUtils::ConstructHeaderAndBodyL() |
|
526 { |
|
527 if (!iParaFormat) |
|
528 iParaFormat = CParaFormatLayer::NewL(); |
|
529 |
|
530 if (!iCharFormat) |
|
531 iCharFormat = CCharFormatLayer::NewL(); |
|
532 |
|
533 if (!iBody) |
|
534 iBody = CRichText::NewL(iParaFormat, iCharFormat); |
|
535 |
|
536 if (!iHeader) |
|
537 iHeader = CSmsHeader::NewL(CSmsPDU::ESmsDeliver, *iBody); |
|
538 } |
|
539 |
|
540 void CSmsSimUtils::RestoreSimUtilsDataL() |
|
541 /** |
|
542 * Restore iSimUtilsData from the SMS service entry |
|
543 * Does not attempt to restore if the stream is not present |
|
544 */ |
|
545 { |
|
546 User::LeaveIfError(iServerEntry.SetEntry(iSmsServiceId)); |
|
547 CMsvStore* store = iServerEntry.ReadStoreL(); |
|
548 CleanupStack::PushL(store); |
|
549 |
|
550 if (iSimUtilsData.IsPresentL(*store)) |
|
551 { |
|
552 iSimUtilsData.RestoreL(*store); |
|
553 } |
|
554 |
|
555 CleanupStack::PopAndDestroy(store); |
|
556 } |
|
557 |
|
558 void CSmsSimUtils::StoreSimUtilsDataL() |
|
559 /** |
|
560 * Store iSimUtilsData against the SMS service entry |
|
561 */ |
|
562 { |
|
563 User::LeaveIfError(iServerEntry.SetEntry(iSmsServiceId)); |
|
564 CMsvStore* store = iServerEntry.EditStoreL(); |
|
565 CleanupStack::PushL(store); |
|
566 iSimUtilsData.StoreL(*store); |
|
567 store->CommitL(); |
|
568 CleanupStack::PopAndDestroy(store); |
|
569 } |
|
570 |
|
571 void CSmsSimUtils::DeleteFromPhoneStoreL(const CMsvEntrySelection& aSelection, TRequestStatus& aStatus) |
|
572 { |
|
573 SMSSLOG(FLogFormat(_L8("Deleting %d messages from SIM"), aSelection.Count())); |
|
574 |
|
575 SetupMoveDeleteL(aSelection, aStatus); |
|
576 DoDeleteFromPhoneStoreL(); |
|
577 } |
|
578 |
|
579 void CSmsSimUtils::DoDeleteFromPhoneStoreL() |
|
580 { |
|
581 iProgress.iType = TSmsProgress::ESmsProgressTypeDeleteFromPhoneStore; |
|
582 |
|
583 ConnectL(); |
|
584 RequestComplete(&iStatus, KErrNone, ETrue); |
|
585 } |
|
586 |
|
587 void CSmsSimUtils::DoDeleteThenMoveFromPhoneStoreL() |
|
588 { |
|
589 iProgress.iType = TSmsProgress::ESmsProgressTypeMoveFromPhoneStore; |
|
590 |
|
591 ConnectL(); |
|
592 RequestComplete(&iStatus, KErrNone, ETrue); |
|
593 } |
|
594 |
|
595 void CSmsSimUtils::LoadClass2FolderIdL() |
|
596 { |
|
597 RestoreSmsSettingsL(); |
|
598 iClass2Folder = iSettings->Class2Folder(); |
|
599 } |
|
600 |
|
601 void CSmsSimUtils::RestoreSmsSettingsL() |
|
602 { |
|
603 CSmsAccount* account = CSmsAccount::NewLC(); |
|
604 // just v2 |
|
605 account->LoadSettingsL(*iSettings); |
|
606 CleanupStack::PopAndDestroy(account); |
|
607 } |
|
608 |
|
609 void CSmsSimUtils::CopyToPhoneStoreL(const CMsvEntrySelection& aSelection, const TDesC8& /*aParameter*/, TRequestStatus& aStatus) |
|
610 { |
|
611 SMSSLOG(FLogFormat(_L8("Copying messages to SIM"))); |
|
612 |
|
613 __ASSERT_DEBUG(aSelection.Count(), Panic(KSmssPanicNoMessagesInSelection)); |
|
614 |
|
615 SetupMoveDeleteL(aSelection,aStatus); |
|
616 iProgress.iType = TSmsProgress::ESmsProgressTypeCopyToPhoneStore; |
|
617 iProgress.iMsgCount = iSelection->Count(); |
|
618 iProgress.iMsgDone = -1; |
|
619 iState=EWritingToSIM; |
|
620 iRecipientCount = 0; |
|
621 iRecipientIndex = 0; |
|
622 |
|
623 LoadClass2FolderIdL(); |
|
624 |
|
625 ConnectL(); |
|
626 ConstructHeaderAndBodyL(); |
|
627 CreateBioDbL(); |
|
628 |
|
629 DoCopyToPhoneStoreL(); |
|
630 } |
|
631 |
|
632 void CSmsSimUtils::MoveToPhoneStoreL(const CMsvEntrySelection& aSelection, const TDesC8& /*aParameter*/, TRequestStatus& aStatus) |
|
633 { |
|
634 SMSSLOG(FLogFormat(_L8("Moving messages to SIM"))); |
|
635 |
|
636 __ASSERT_DEBUG(aSelection.Count(), Panic(KSmssPanicNoMessagesInSelection)); |
|
637 |
|
638 SetupMoveDeleteL(aSelection,aStatus); |
|
639 iProgress.iType = TSmsProgress::ESmsProgressTypeMoveToPhoneStore; |
|
640 iProgress.iMsgCount = iSelection->Count(); |
|
641 iProgress.iMsgDone = -1; |
|
642 iState=EWritingToSIM; |
|
643 iRecipientCount = 0; |
|
644 iRecipientIndex = 0; |
|
645 |
|
646 LoadClass2FolderIdL(); |
|
647 |
|
648 ConnectL(); |
|
649 ConstructHeaderAndBodyL(); |
|
650 CreateBioDbL(); |
|
651 |
|
652 DoCopyToPhoneStoreL(); |
|
653 } |
|
654 |
|
655 |
|
656 void CSmsSimUtils::DoCopyToPhoneStoreL() |
|
657 { |
|
658 User::LeaveIfError(iServerEntry.SetEntry(KMsvNullIndexEntryId)); |
|
659 if(iState==EWritingToSIM) |
|
660 { |
|
661 if (iRecipientCount == 0) |
|
662 ++iProgress.iMsgDone; |
|
663 |
|
664 if (iProgress.iMsgDone < iProgress.iMsgCount) |
|
665 { |
|
666 User::LeaveIfError(iServerEntry.SetEntry(iSelection->At(iProgress.iMsgDone))); |
|
667 |
|
668 CMsvStore* store = iServerEntry.ReadStoreL(); |
|
669 CleanupStack::PushL(store); |
|
670 |
|
671 iHeader->RestoreL(*store); |
|
672 iBody->Reset(); |
|
673 store->RestoreBodyTextL(*iBody); |
|
674 |
|
675 CleanupStack::PopAndDestroy(); //store |
|
676 |
|
677 // Set correct address on the CSmsMessage if it out going |
|
678 CSmsMessage& smsmessage=iHeader->Message(); |
|
679 if (smsmessage.Type()==CSmsPDU::ESmsSubmit || (smsmessage.Type()==CSmsPDU::ESmsCommand)) |
|
680 { |
|
681 // Get the count of recipients for the current message |
|
682 if (iRecipientCount == 0) |
|
683 { |
|
684 iRecipientCount = iHeader->Recipients().Count(); |
|
685 iRecipientIndex = 0; |
|
686 } |
|
687 // Create separate copy of message for each recipient |
|
688 if (iRecipientCount > 0) |
|
689 { |
|
690 CSmsNumber& rcpt = *iHeader->Recipients().At(iRecipientIndex); |
|
691 iHeader->Message().SetToFromAddressL(rcpt.Address()); |
|
692 } |
|
693 ++iRecipientIndex; |
|
694 // Check if all the recipients are processed |
|
695 if (iRecipientIndex >= iRecipientCount) |
|
696 { |
|
697 // Yes all are done |
|
698 iRecipientIndex = 0; |
|
699 iRecipientCount = 0; |
|
700 } |
|
701 } |
|
702 SMSSLOG(FLogMessage(iServerEntry.Entry(), iHeader->Message(), iHeader->BioMsgIdType(), KCopyToSimLog)); |
|
703 |
|
704 smsmessage.SetStorage(CSmsMessage::ESmsSIMStorage); //Set to store on SIM |
|
705 |
|
706 if (iServerEntry.Entry().Unread()) |
|
707 { |
|
708 smsmessage.SetStatus(NMobileSmsStore::EStoredMessageUnread); |
|
709 } |
|
710 else |
|
711 { |
|
712 smsmessage.SetStatus(NMobileSmsStore::EStoredMessageRead); |
|
713 } |
|
714 |
|
715 // This may be a BIO message, so test and set up SMS message correctly! |
|
716 if ((smsmessage.Type()==CSmsPDU::ESmsSubmit) || (smsmessage.Type()==CSmsPDU::ESmsDeliver)) |
|
717 EncodeBioMessageL(); |
|
718 |
|
719 iWriteStream << iHeader->Message(); |
|
720 iWriteStream.CommitL(); |
|
721 iSocket.Ioctl(KIoctlWriteSmsMessage, iStatus, &iSlotBuffer, KSolSmsProv); |
|
722 SetActive(); |
|
723 |
|
724 // if we have a class 2 folder, and its not the current parent |
|
725 // then update the class 2 folder with the new message one the sim |
|
726 if(iClass2Folder!=KMsvNullIndexEntryId && |
|
727 iClass2Folder != iServerEntry.Entry().Parent()) |
|
728 iState=EUpdatingClass2; |
|
729 else |
|
730 iState=EWritingToSIM; |
|
731 } |
|
732 } |
|
733 else |
|
734 { |
|
735 __ASSERT_DEBUG(iState==EUpdatingClass2,Panic(ESmssBadState)); |
|
736 __ASSERT_DEBUG(iClass2Folder!=KMsvNullIndexEntryId,Panic(ESmssNoClass2Folder)); |
|
737 TMsvId toCopy=iSelection->At(iProgress.iMsgDone); |
|
738 User::LeaveIfError(iServerEntry.SetEntry(toCopy)); |
|
739 |
|
740 // Update the slot array of the CSmsMessage so that |
|
741 // it can be deleted at a later time without the need for a re-enumeration |
|
742 TMsvEntry entry = iServerEntry.Entry(); |
|
743 TBool wasReadOnly = entry.ReadOnly(); |
|
744 |
|
745 if (wasReadOnly) |
|
746 { |
|
747 entry.SetReadOnly(EFalse); |
|
748 iServerEntry.ChangeEntry(entry); |
|
749 } |
|
750 |
|
751 CMsvStore* store = iServerEntry.EditStoreL(); |
|
752 CleanupStack::PushL(store); |
|
753 iHeader->RestoreL(*store); |
|
754 CSmsMessage& smsmessage=iHeader->Message(); |
|
755 |
|
756 smsmessage.UpdateSlotsL(iSlotBuffer); |
|
757 smsmessage.SetStorage(CSmsMessage::ESmsSIMStorage); |
|
758 iHeader->StoreL(*store); |
|
759 store->CommitL(); |
|
760 |
|
761 if (wasReadOnly) |
|
762 { |
|
763 entry.SetReadOnly(ETrue); |
|
764 iServerEntry.ChangeEntry(entry); |
|
765 } |
|
766 |
|
767 CleanupStack::PopAndDestroy(store); |
|
768 User::LeaveIfError(iServerEntry.SetEntry(iServerEntry.Entry().Parent())); |
|
769 |
|
770 if(iProgress.iType == TSmsProgress::ESmsProgressTypeMoveToPhoneStore) |
|
771 iServerEntry.MoveEntryL(toCopy,iClass2Folder,iStatus); |
|
772 else |
|
773 iServerEntry.CopyEntryL(toCopy,iClass2Folder,iStatus); |
|
774 |
|
775 SetActive(); |
|
776 iState=EWritingToSIM; |
|
777 } |
|
778 } |
|
779 |
|
780 void CSmsSimUtils::CopyFromPhoneStoreL(const CMsvEntrySelection& aSelection, const TDesC8& aParameter, TRequestStatus& aStatus) |
|
781 { |
|
782 SMSSLOG(FLogFormat(_L8("Copying messages from phone store"))); |
|
783 __ASSERT_DEBUG(aSelection.Count(), Panic(KSmssPanicNoMessagesInSelection)); |
|
784 |
|
785 SetupMoveDeleteL(aSelection, aStatus); |
|
786 iProgress.iType = TSmsProgress::ESmsProgressTypeCopyFromPhoneStore; |
|
787 SetDestination(aParameter); |
|
788 MoveEntriesL(*iSelection, ETrue); |
|
789 } |
|
790 |
|
791 void CSmsSimUtils::MoveEntriesL(const CMsvEntrySelection& aSelection, TBool aCopy) |
|
792 { |
|
793 // Uses the enumeration folder under the service to copy from |
|
794 User::LeaveIfError(iServerEntry.SetEntry(aSelection[0])); |
|
795 User::LeaveIfError(iServerEntry.SetEntry(iServerEntry.Entry().Parent())); |
|
796 if (aCopy) |
|
797 { |
|
798 if (iCompletedSelection) |
|
799 iCompletedSelection->Reset(); |
|
800 else |
|
801 iCompletedSelection = new(ELeave) CMsvEntrySelection; |
|
802 |
|
803 iServerEntry.CopyEntriesL(aSelection, iDestination, *iCompletedSelection, iStatus); |
|
804 } |
|
805 else |
|
806 iServerEntry.MoveEntriesL(aSelection, iDestination, iStatus); |
|
807 SetActive(); |
|
808 } |
|
809 |
|
810 void CSmsSimUtils::MoveFromPhoneStoreL(const CMsvEntrySelection& aSelection, const TDesC8& aParameter, TRequestStatus& aStatus) |
|
811 { |
|
812 SMSSLOG(FLogFormat(_L8("Moving messages from phone store"))); |
|
813 __ASSERT_DEBUG(aSelection.Count(), Panic(KSmssPanicNoMessagesInSelection)); |
|
814 |
|
815 SetupMoveDeleteL(aSelection, aStatus); |
|
816 iProgress.iType = TSmsProgress::ESmsProgressTypeMoveFromPhoneStore; |
|
817 SetDestination(aParameter); |
|
818 |
|
819 DoDeleteThenMoveFromPhoneStoreL(); |
|
820 } |
|
821 |
|
822 void CSmsSimUtils::SetDestination(const TDesC8& aParameter) |
|
823 { |
|
824 TPckgBuf<TMsvId> pkg; |
|
825 pkg.Copy(aParameter); |
|
826 iDestination = pkg(); |
|
827 __ASSERT_DEBUG(iDestination, Panic(KSmssPanicDestinationFolderNotSet)); |
|
828 } |
|
829 |
|
830 void CSmsSimUtils::SetLocalStorageInfoL(const CMsvEntrySelection& aSelection) |
|
831 { |
|
832 // After a copy/move from phone store the iSlotArray and Storage members |
|
833 // need to be reset to reflect the local storage. |
|
834 __ASSERT_DEBUG(aSelection.Count(), Panic(KSmssPanicNoMessagesInSelection)); |
|
835 TInt count = aSelection.Count(); |
|
836 ConstructHeaderAndBodyL(); |
|
837 TBool wasReadOnly = EFalse; |
|
838 |
|
839 while (count--) |
|
840 { |
|
841 // RetrieveMessageFromPhoneStoreL() may have set the TMsvEntry |
|
842 // to read only if the message is a CSmsPDU::ESmsSubmit |
|
843 iServerEntry.SetEntry(aSelection.At(count)); |
|
844 TMsvEntry entry = iServerEntry.Entry(); |
|
845 wasReadOnly = entry.ReadOnly(); |
|
846 |
|
847 if (wasReadOnly) |
|
848 { |
|
849 entry.SetReadOnly(EFalse); |
|
850 iServerEntry.ChangeEntry(entry); |
|
851 } |
|
852 |
|
853 CMsvStore* store = iServerEntry.EditStoreL(); |
|
854 CleanupStack::PushL(store); |
|
855 iHeader->RestoreL(*store); |
|
856 CSmsMessage& smsmessage = iHeader->Message(); |
|
857 |
|
858 // Set the destination attributes |
|
859 smsmessage.SetStorage(CSmsMessage::ESmsPhoneStorage); |
|
860 smsmessage.iSlotArray.Reset(); |
|
861 |
|
862 iHeader->StoreL(*store); |
|
863 store->CommitL(); |
|
864 CleanupStack::PopAndDestroy(store); |
|
865 |
|
866 if (wasReadOnly) |
|
867 { |
|
868 entry.SetReadOnly(ETrue); |
|
869 iServerEntry.ChangeEntry(entry); |
|
870 } |
|
871 } |
|
872 } |
|
873 |
|
874 void CSmsSimUtils::ConnectL() |
|
875 { |
|
876 ConnectL(iSocketServ, iSocket, ESmsAddrLocalOperation); |
|
877 } |
|
878 |
|
879 void CSmsSimUtils::ConnectL(RSocketServ& arSocketServ, RSocket& arSocket, TSmsAddrFamily aSmsAddrFamily) |
|
880 { |
|
881 if (!arSocketServ.Handle()) |
|
882 { |
|
883 User::LeaveIfError(arSocketServ.Connect()); |
|
884 } |
|
885 |
|
886 TProtocolDesc protoinfo; |
|
887 TProtocolName protocolname(KSmsDatagram); |
|
888 User::LeaveIfError(arSocketServ.FindProtocol(protocolname,protoinfo)); |
|
889 |
|
890 if (!arSocket.SubSessionHandle()) |
|
891 { |
|
892 User::LeaveIfError(arSocket.Open(arSocketServ,protoinfo.iAddrFamily,protoinfo.iSockType,protoinfo.iProtocol)); |
|
893 } |
|
894 |
|
895 TSmsAddr smsaddr; |
|
896 smsaddr.SetSmsAddrFamily(aSmsAddrFamily); |
|
897 User::LeaveIfError(arSocket.Bind(smsaddr)); |
|
898 } |
|
899 |
|
900 |
|
901 CSmsSimUtils::CSmsSimUtils(CMsvServerEntry& aServerEntry, RFs& aFs, TMsvId aSmsServiceId) |
|
902 : CSmssActive(aFs, aServerEntry), |
|
903 iState(ESimUtilsStateOther), |
|
904 iReadStream(iSocket), |
|
905 iSmsServiceId(aSmsServiceId), |
|
906 iWriteStream(iSocket) |
|
907 { |
|
908 CActiveScheduler::Add(this); |
|
909 } |
|
910 |
|
911 void CSmsSimUtils::DoRunReadSimParamsL() |
|
912 /** |
|
913 Retrive and store the parameters to the message store. |
|
914 |
|
915 @since 7.0 |
|
916 @leave KErrNotFound |
|
917 @pre The reading async operation is complete. |
|
918 @post The parameters are retrived and stored in the message store. |
|
919 */ |
|
920 { |
|
921 iProgress.iMsgDone = iSmsServiceId; |
|
922 |
|
923 CMobilePhoneSmspList* smspList = CMobilePhoneSmspList::NewL(); |
|
924 CleanupStack::PushL(smspList); |
|
925 |
|
926 iReadStream >> *smspList; |
|
927 |
|
928 iProgress.iMsgCount = smspList->Enumerate(); |
|
929 |
|
930 if (!iProgress.iMsgCount) |
|
931 User::Leave(KErrNotFound); |
|
932 |
|
933 User::LeaveIfError(iServerEntry.SetEntry(iSmsServiceId)); |
|
934 |
|
935 CMsvStore* store = iServerEntry.EditStoreL(); |
|
936 CleanupStack::PushL(store); |
|
937 |
|
938 CSmsSimParamOperation::StoreSimParamsL(*store, *smspList); |
|
939 |
|
940 CleanupStack::PopAndDestroy(2); //smspList, store |
|
941 User::LeaveIfError(iServerEntry.SetEntry(KMsvNullIndexEntryId)); |
|
942 } |
|
943 |
|
944 void CSmsSimUtils::DoRunL() |
|
945 /** |
|
946 Handles completed async operations |
|
947 |
|
948 @since 7.0 |
|
949 @leave ESmscPanicUnexpectedCommand, KErrNone |
|
950 @pre The async operation is complete |
|
951 @post The operation is complete |
|
952 */ |
|
953 { |
|
954 switch (iProgress.iType) |
|
955 { |
|
956 case TSmsProgress::ESmsProgressTypeCopyFromPhoneStore: |
|
957 { |
|
958 __ASSERT_DEBUG(iCompletedSelection, Panic(KSmssPanicNoMessagesInSelection)); |
|
959 SetLocalStorageInfoL(*iCompletedSelection); |
|
960 break; |
|
961 } |
|
962 case TSmsProgress::ESmsProgressTypeWriteSimParams: |
|
963 { |
|
964 break; |
|
965 } |
|
966 case TSmsProgress::ESmsProgressTypeReadSimParams: |
|
967 { |
|
968 if (iReadingSimParams) |
|
969 { |
|
970 iReadingSimParams = EFalse; |
|
971 TRAP(iProgress.iError, DoRunReadSimParamsL()); |
|
972 iSocket.Ioctl(KIoctlCompleteReadSmsParams, iStatus, NULL, KSolSmsProv); |
|
973 SetActive(); |
|
974 } |
|
975 break; |
|
976 } |
|
977 case TSmsProgress::ESmsProgressTypeEnumeratingPhoneStores: |
|
978 { |
|
979 iProgress.iMsgCount = iEnumerateCountBuf(); |
|
980 RetrieveMessageFromPhoneStoreL(); |
|
981 break; |
|
982 } |
|
983 case TSmsProgress::ESmsProgressTypeDeleteFromPhoneStore: |
|
984 { |
|
985 DeleteEachMessageFromPhoneStoreL(); |
|
986 break; |
|
987 } |
|
988 case TSmsProgress::ESmsProgressTypeMoveFromPhoneStore: |
|
989 { |
|
990 DeleteEachMessageFromPhoneStoreL(); |
|
991 |
|
992 if (iState == ESimUtilsDeletedLastMessage) |
|
993 { |
|
994 // We have finished deleting the messages from the SIM so set |
|
995 // the Storage & iSlotArray then move the entries |
|
996 SetLocalStorageInfoL(*iSelection); |
|
997 iState = ESimUtilsStateOther; |
|
998 iProgress.iType = TSmsProgress::ESmsProgressTypeMovingEntries; |
|
999 MoveEntriesL(*iSelection, EFalse); |
|
1000 } |
|
1001 break; |
|
1002 } |
|
1003 case TSmsProgress::ESmsProgressTypeCopyToPhoneStore: |
|
1004 case TSmsProgress::ESmsProgressTypeMoveToPhoneStore: |
|
1005 { |
|
1006 DoCopyToPhoneStoreL(); |
|
1007 break; |
|
1008 } |
|
1009 case TSmsProgress::ESmsProgressTypeMovingEntries: |
|
1010 break; |
|
1011 default: |
|
1012 { |
|
1013 Panic(KSmssPanicUnexpectedState); |
|
1014 } |
|
1015 } |
|
1016 } |
|
1017 |
|
1018 void CSmsSimUtils::RetrieveMessageFromPhoneStoreL() |
|
1019 { |
|
1020 // If one message fails to be restored the rest fail |
|
1021 if (iProgress.iMsgDone < iProgress.iMsgCount) |
|
1022 { |
|
1023 CSmsMessage& smsmessage=iHeader->Message(); |
|
1024 iReadStream >> smsmessage; |
|
1025 |
|
1026 TUid biomsguid=KNullUid; |
|
1027 TBioMsgId id; |
|
1028 if ((smsmessage.Type()==CSmsPDU::ESmsSubmit) || (smsmessage.Type()==CSmsPDU::ESmsDeliver)) |
|
1029 biomsguid=DecodeBioMessageL(id); |
|
1030 |
|
1031 TMsvEntry entry; |
|
1032 RestoreSmsSettingsL(); |
|
1033 TInt length = iSettings->DescriptionLength(); |
|
1034 HBufC* buf = HBufC::NewLC(length); |
|
1035 TPtr description = buf->Des(); |
|
1036 |
|
1037 if (biomsguid != KNullUid) |
|
1038 { |
|
1039 TSmsUtilities::PopulateMsgEntry(entry, smsmessage, iSmsServiceId, *iSettings, KUidBIOMessageTypeMtm); |
|
1040 |
|
1041 // BioficateEntry!!! |
|
1042 // Set up all the needed ids |
|
1043 entry.iBioType = biomsguid.iUid; |
|
1044 entry.iServiceId = KMsvLocalServiceIndexEntryId; |
|
1045 entry.iMtm = KUidBIOMessageTypeMtm; |
|
1046 |
|
1047 // Look up and set the description |
|
1048 TInt index; |
|
1049 iBioDb->GetBioIndexWithMsgIDL(biomsguid, index); |
|
1050 description.Copy(iBioDb->BifReader(index).Description().Left(length)); |
|
1051 } |
|
1052 else |
|
1053 { |
|
1054 // Set the details |
|
1055 TSmsUtilities::PopulateMsgEntry(entry, smsmessage, iSmsServiceId, *iSettings); |
|
1056 |
|
1057 iGetDetDesc->GetDescription(smsmessage, description, length); |
|
1058 } |
|
1059 |
|
1060 entry.iDescription.Set(description); |
|
1061 |
|
1062 if (smsmessage.Status() == NMobileSmsStore::EStoredMessageUnread) |
|
1063 entry.SetUnread(ETrue); |
|
1064 else |
|
1065 entry.SetUnread(EFalse); |
|
1066 |
|
1067 TBuf<KSmsDetailsLength> details; |
|
1068 if (iGetDetDesc->GetDetails(iFs, smsmessage, details) == KErrNone) |
|
1069 entry.iDetails.Set(details); |
|
1070 |
|
1071 User::LeaveIfError(iServerEntry.SetEntry(iProgress.iEnumerateFolder)); |
|
1072 User::LeaveIfError(iServerEntry.CreateEntry(entry)); |
|
1073 User::LeaveIfError(iServerEntry.SetEntry(entry.Id())); |
|
1074 CMsvStore* store = iServerEntry.EditStoreL(); |
|
1075 CleanupStack::PushL(store); |
|
1076 store->StoreBodyTextL(*iBody); |
|
1077 iHeader->StoreL(*store); |
|
1078 store->CommitL(); |
|
1079 |
|
1080 if (iHeader->Type() != CSmsPDU::ESmsSubmit) |
|
1081 { |
|
1082 entry.SetReadOnly(ETrue); |
|
1083 } |
|
1084 |
|
1085 entry.iSize = store->SizeL(); |
|
1086 CleanupStack::PopAndDestroy(store); |
|
1087 User::LeaveIfError(iServerEntry.ChangeEntry(entry)); |
|
1088 |
|
1089 SMSSLOG(FLogMessage(entry, iHeader->Message(), iHeader->BioMsgIdType(), KEnumerateSimLog)); |
|
1090 |
|
1091 User::LeaveIfError(iServerEntry.SetEntry(KMsvNullIndexEntryId)); |
|
1092 |
|
1093 iSocket.Ioctl(KIoctlReadMessageSucceeded, iStatus, NULL, KSolSmsProv); |
|
1094 SetActive(); |
|
1095 |
|
1096 iProgress.iMsgDone++; |
|
1097 |
|
1098 SMSSLOG(FLogFormat(_L8("\tRead %d from SIM (%d/%d)"), entry.Id(), iProgress.iMsgDone, iProgress.iMsgCount)); |
|
1099 |
|
1100 CleanupStack::PopAndDestroy(buf); |
|
1101 } |
|
1102 } |
|
1103 |
|
1104 void CSmsSimUtils::DoComplete(TInt& aStatus) |
|
1105 { |
|
1106 if (iState == ESimUtilsDeleteEachMessage && aStatus == KErrNotFound) |
|
1107 { |
|
1108 #ifndef _MSG_NO_LOGGING |
|
1109 const TMsvId id = iServerEntry.Entry().Id(); |
|
1110 _LIT(KLogTxt, "\tERROR: %d NOT deleted from the SIM. Error=KErrNotFound"); |
|
1111 SMSSLOG(FLogFormat(KDeleteFromSimLog, KLogTxt, id)); |
|
1112 SMSSLOG(FLogFormat(KLogTxt, id)); |
|
1113 #endif |
|
1114 |
|
1115 TRAP(iProgress.iError, DeleteEachMessageFromPhoneStoreL()); |
|
1116 } |
|
1117 else if (aStatus != KErrNone) |
|
1118 { |
|
1119 iServerEntry.SetEntry(KMsvNullIndexEntryId); |
|
1120 iProgress.iError = aStatus; |
|
1121 } |
|
1122 |
|
1123 #ifndef _MSG_NO_LOGGING |
|
1124 if (!IsActive()) |
|
1125 SMSSLOG(FLogFormat(_L8("SmsSimUtils completed. Error %d, MsgCount %d, MsgDone %d"), iProgress.iError, iProgress.iMsgCount, iProgress.iMsgDone)); |
|
1126 #endif |
|
1127 |
|
1128 aStatus = KErrNone; |
|
1129 } |
|
1130 |
|
1131 void CSmsSimUtils::DoSmssCancel() |
|
1132 { |
|
1133 if (iSocket.SubSessionHandle()) |
|
1134 iSocket.CancelIoctl(); |
|
1135 } |
|
1136 |
|
1137 |
|
1138 /** |
|
1139 * TSmsSimUtilsData |
|
1140 */ |
|
1141 |
|
1142 void TSmsSimUtilsData::StoreL(CMsvStore& aStore) const |
|
1143 { |
|
1144 RMsvWriteStream writeStream; |
|
1145 writeStream.AssignLC(aStore, KSmsSimUtilsDataUid); |
|
1146 ExternalizeL(writeStream); |
|
1147 writeStream.CommitL(); |
|
1148 CleanupStack::PopAndDestroy(&writeStream); |
|
1149 } |
|
1150 |
|
1151 void TSmsSimUtilsData::RestoreL(const CMsvStore& aStore) |
|
1152 { |
|
1153 RMsvReadStream readStream; |
|
1154 readStream.OpenLC(aStore, KSmsSimUtilsDataUid); |
|
1155 InternalizeL(readStream); |
|
1156 CleanupStack::PopAndDestroy(&readStream); |
|
1157 } |
|
1158 |
|
1159 void TSmsSimUtilsData::ExternalizeL(RWriteStream& aStream) const |
|
1160 { |
|
1161 aStream.WriteInt16L(KSmsSimUtilsDataVersion); |
|
1162 aStream.WriteInt32L(iLastEnumerateFolder); |
|
1163 } |
|
1164 |
|
1165 void TSmsSimUtilsData::InternalizeL(RReadStream& aStream) |
|
1166 { |
|
1167 aStream.ReadInt16L(); // version, not used until version > 1 |
|
1168 iLastEnumerateFolder = aStream.ReadInt32L(); |
|
1169 } |
|