diff -r b183ec05bd8c -r 19bba8228ff0 fotaapplication/fotaserver/src/fotaupdate.cpp --- a/fotaapplication/fotaserver/src/fotaupdate.cpp Tue Aug 31 16:04:06 2010 +0300 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,722 +0,0 @@ -/* - * Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). - * All rights reserved. - * This component and the accompanying materials are made available - * under the terms of "Eclipse Public License v1.0" - * which accompanies this distribution, and is available - * at the URL "http://www.eclipse.org/legal/epl-v10.html". - * - * Initial Contributors: - * Nokia Corporation - initial contribution. - * - * Contributors: - * - * Description: starts update sequence - * - */ - -// INCLUDE FILES -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include "fotaupdate.h" -#include "fmsclient.h" -#include "FotasrvSession.h" -#include "fotaserverPrivateCRKeys.h" -#include "fotaserverPrivatePSKeys.h" -#include "fotanotifiers.h" - -#include -#include -// ============================= MEMBER FUNCTIONS ============================ - - -// --------------------------------------------------------------------------- -// CFotaUpdate::CFotaUpdate() -// --------------------------------------------------------------------------- -// -CFotaUpdate::CFotaUpdate() : - CActive(EPriorityNormal) - { - CActiveScheduler::Add(this); - } - -// --------------------------------------------------------------------------- -// CFotaUpdate::~CFotaUpdate() -// --------------------------------------------------------------------------- -// -CFotaUpdate::~CFotaUpdate() - { - FLOG(_L("CFotaUpdate::~CFotaUpdate >>")); - iFotaServer = NULL; - - CancelMonitor(); - - if (iProperty.Handle()) - iProperty.Close(); - - FLOG(_L("CFotaUpdate::~CFotaUpdate <<")); - } - -// --------------------------------------------------------------------------- -// CFotaUpdate::NewL -// --------------------------------------------------------------------------- -// -CFotaUpdate* CFotaUpdate::NewL(CFotaServer* aServer) - { - CFotaUpdate* ao = new (ELeave) CFotaUpdate(); - ao->iFotaServer = aServer; - return ao; - } - -// --------------------------------------------------------------------------- -// CFotaUpdate::CheckUpdateResults -// Checks if there is update result file available (meaning that update just -// took place) -// --------------------------------------------------------------------------- -// -TBool CFotaUpdate::CheckUpdateResults(RFs& aRfs) - { - RFile f; - TInt err; - err = f.Open(aRfs, KUpdateResultFile, EFileShareAny); - f.Close(); - if (err != KErrNone) - { - return EFalse; - } - FLOG(_L(" CFotaUpdate::CheckUpdateResults update result file Found! ")); - return ETrue; - } - -// --------------------------------------------------------------------------- -// CFotaUpdate::ExecuteUpdateResultFileL -// Read result code from update result file and update state accordingly. -// Show notifier "Update succesful". Do some cleanup. -// --------------------------------------------------------------------------- -// -void CFotaUpdate::ExecuteUpdateResultFileL() - { - FLOG(_L("CFotaUpdate::ExecuteUpdateResultFileL >>")); - - TInt err; - RFileReadStream rstr; - TInt result; - TInt msglen; - HBufC8* message = NULL; - HBufC16* message16 = NULL; - TBool deleteData(EFalse); - - // Open update result file - FLOG(_L("opening rstr 1/2 ")); - err = rstr.Open(iFotaServer->iFs, KUpdateResultFile, EFileRead - | EFileStream); - FLOG(_L("opened rstr 2/2 ")); - if (err) - { - FLOG(_L(" update result file open err %d"), err); - } - User::LeaveIfError(err); - FLOG(_L(" 0.1")); - CleanupClosePushL(rstr); - FLOG(_L(" 0.2")); - - // Read resultcode - result = rstr.ReadUint32L(); - msglen = rstr.ReadUint32L(); - if (msglen != 0) - { - message = HBufC8::NewLC(msglen + 1); - TPtr8 ptrdesc = message->Des(); - TRAPD ( err2, rstr.ReadL(ptrdesc) ); - if (err2 != KErrNone && err2 != KErrEof) - { - FLOG(_L(" file read err %d"), err2); - User::Leave(err2); - } - - message16 = HBufC16::NewLC(message->Des().Length()); - message16->Des().Copy(*message); - FLOG(_L(" 1 update result: %d"), result); - FLOG(_L(" 2 dbg msg: %S"), message16); - CleanupStack::PopAndDestroy(message16); - CleanupStack::PopAndDestroy(message); - } - - FLOG(_L(" 0.6 ")); - CleanupStack::PopAndDestroy(&rstr); - - // Map resultcode to FUMO result code - RFotaEngineSession::TState fstate = RFotaEngineSession::EUpdateFailed; - RFotaEngineSession::TResult fresult = - RFotaEngineSession::EResUpdateFailed; - - FLOG(_L(" 3")); - switch (result) - { - case UPD_OK: - { - fstate = RFotaEngineSession::EUpdateSuccessfulNoData; - fresult = RFotaEngineSession::EResSuccessful; - deleteData = ETrue; - ShowDialogL(EFwUpdSuccess); - } - break; - case UPD_INSTALL_REQUEST_IS_INVALID: - { - fstate = RFotaEngineSession::EUpdateFailedNoData; - fresult = RFotaEngineSession::EResUpdateFailed; - deleteData = ETrue; - ShowDialogL(EFwUpdNotCompatible); - } - break; - case UPD_UPDATE_PACKAGE_IS_ABSENT: - { - fstate = RFotaEngineSession::EUpdateFailedNoData; - fresult = RFotaEngineSession::EResUpdateFailed; - ShowDialogL(EFwUpdNotCompatible); - } - break; - case UPD_UPDATE_PACKAGE_IS_CORRUPTED: - { - fstate = RFotaEngineSession::EUpdateFailedNoData; - fresult = RFotaEngineSession::EResCorruptedFWUPD; - deleteData = ETrue; - ShowDialogL(EFwUpdNotCompatible); - } - break; - case UPD_UPDATE_PACKAGE_CONTENTS_IS_INVALID: - { - fstate = RFotaEngineSession::EUpdateFailedNoData; - fresult = RFotaEngineSession::EResCorruptedFWUPD; - deleteData = ETrue; - ShowDialogL(EFwUpdNotCompatible); - } - break; - case UPD_UPDATE_PACKAGE_IS_NOT_COMPATIBLE_WITH_CURRENT_MOBILE_DEVICE: - { - fstate = RFotaEngineSession::EUpdateFailedNoData; - fresult = RFotaEngineSession::EResPackageMismatch; - deleteData = ETrue; - ShowDialogL(EFwUpdNotCompatible); - } - break; - case UPD_FATAL_ERROR: - { - fstate = RFotaEngineSession::EUpdateFailedNoData; - fresult = RFotaEngineSession::EResUpdateFailed; - deleteData = ETrue; - ShowDialogL(EFwUpdNotCompatible); - } - break; - - default: - { - FLOG(_L(" 3.1 invalid result: %d"), result); - fstate = RFotaEngineSession::EUpdateFailedNoData; - fresult = RFotaEngineSession::EResUpdateFailed; - deleteData = ETrue; - ShowDialogL(EFwUpdNotCompatible); - } - break; - } - - // Find the state 60 (update progressing) -> 100 (etc) - RArray states; - TPackageState state; - CleanupClosePushL(states); - iFotaServer->iDatabase->OpenDBL(); - iFotaServer->iDatabase->GetAllL(states); - - FLOG(_L(" 4.1 found %d states "), states.Count()); - for (TInt i = 0; i < states.Count(); ++i) - { - TPackageState tmp; - TBuf8 tmpurl; - tmp = iFotaServer->iDatabase->GetStateL(states[i], tmpurl); - FLOG(_L(" 5 got state ")); - if (tmp.iState == RFotaEngineSession::EUpdateProgressing) - { - state = tmp; - state.iState = fstate; - state.iResult = fresult; - FLOG(_L(" 6 Updating state id %d to %d ,result %d "), - state.iPkgId, state.iState, state.iResult); - iFotaServer->iDatabase->SetStateL(state, KNullDesC8, EFDBState - | EFDBResult); - } - } - iFotaServer->iDatabase->CloseAndCommitDB(); - CleanupStack::PopAndDestroy(&states); - - // Delete request file - err = BaflUtils::DeleteFile(iFotaServer->iFs, KUpdateRequestFile); - if (err != KErrNone && err != KErrNotFound) - { - FLOG(_L(" 6.1 req file deleted, err %d"), err); - User::Leave(err); - } - - // Write timestamp (shown to user in device management ui) - if (fresult == RFotaEngineSession::EResSuccessful) - { - RFileWriteStream wstr; - TTime time; - User::LeaveIfError(wstr.Replace(iFotaServer->iFs, - KUpdateTimeStampFileName, EFileWrite)); - CleanupClosePushL(wstr); - time.HomeTime(); - TInt year = time.DateTime().Year(); - TInt month = time.DateTime().Month(); - TInt day = time.DateTime().Day(); - TInt hour = time.DateTime().Hour(); - TInt minute = time.DateTime().Minute(); - wstr.WriteInt32L(year); - wstr.WriteInt32L(month); - wstr.WriteInt32L(day); - wstr.WriteInt32L(hour); - wstr.WriteInt32L(minute); - CleanupStack::PopAndDestroy(1); // wstr - } - // Delete package content - if (deleteData && state.iPkgId > KErrNotFound) - { - iFotaServer->DeletePackageL(state.iPkgId); - DeleteUpdateResultFileL(); - } - - // Report state back to syncml server - if (state.iPkgId >= 0) - { - FLOG(_L(" 6.1 creating device mgmt session for profile %d"), - state.iProfileId); - iFotaServer->ReportFwUpdateStatusL(state); - } - else - { - FLOG(_L(" No state found in 'update progress' mode! cannot report status to DM server ")); - } - - FLOG(_L("CFotaUpdate::ExecuteUpdateResultFileL <<")); - } - -// --------------------------------------------------------------------------- -// CFotaUpdate::DeleteUpdateResultsL -// --------------------------------------------------------------------------- -// -void CFotaUpdate::DeleteUpdateResultFileL() - { - FLOG(_L("CFotaUpdate::DeleteUpdateResultsL >>")); - // Delete result file - RFs fs; - __LEAVE_IF_ERROR(fs.Connect()); - BaflUtils::DeleteFile(fs, KUpdateResultFile); - BaflUtils::DeleteFile(fs, KUpdateRequestFile); - BaflUtils::DeleteFile(fs, KUpdateBitmap); - BaflUtils::DeleteFile(fs, KRestartingBitmap); - fs.Close(); - FLOG(_L("CFotaUpdate::DeleteUpdateResultsL <<")); - } - -// --------------------------------------------------------------------------- -// CFotaUpdate::UpdateL -// Updates the fw: Creates input files for update agent and boots device to -// update mode. -// --------------------------------------------------------------------------- -void CFotaUpdate::UpdateL() - { - FLOG(_L("CFotaUpdate::UpdateL() >>")); - // Set state ........................................ - iFotaServer->iPackageState.iState - = RFotaEngineSession::EUpdateProgressing; - iFotaServer->iDatabase->OpenDBL(); - iFotaServer->iDatabase->SetStateL(iFotaServer->iPackageState, KNullDesC8, - EFDBState); - iFotaServer->iDatabase->CloseAndCommitDB(); - - // Write update request for update agent.............. - FLOG(_L("CFotaUpdate::UpdateL 1 writing update.req ")); - TBuf16 dp2filepath; - HBufC16* dp2; - RFileWriteStream wstr; - CleanupClosePushL(wstr); - FLOG(_L("CFotaUpdate::UpdateL 2 getting pkg location")); - iFotaServer->DownloaderL()->GetUpdatePackageLocation(dp2filepath); - - FLOG(_L("CFotaUpdate::UpdateL 3 craeting update.req")); - User::LeaveIfError(wstr.Replace(iFotaServer->iFs, KUpdateRequestFile, - EFileWrite)); - wstr.WriteInt16L(1); // version number is 1 - wstr.WriteInt32L(1); // count of cmds is 1 - wstr.WriteInt16L(0); // requestid is 0 - - dp2 = HBufC16::NewLC(dp2filepath.Length()); - dp2->Des().Copy(dp2filepath); - wstr.WriteInt32L(dp2->Des().Length() + 1); // length of filename + null - wstr.WriteL(dp2->Des()); - wstr.WriteInt16L(0); // null character - CleanupStack::PopAndDestroy(dp2); - CleanupStack::PopAndDestroy(&wstr); // wstr - - FLOG(_L("CFotaUpdate::UpdateL 4 craeting update.bmp")); - - - // Write update graphic for update agent ............... - HBufC* updatetxt; - HBufC* restarttxt; - QString installstr = hbTrId("txt_device_update_info_installing"); - QString rebootstr = hbTrId("txt_device_update_info_rebooting"); - updatetxt = XQConversions::qStringToS60Desc(installstr); - restarttxt = XQConversions::qStringToS60Desc(rebootstr); - - WriteUpdateBitmapL( updatetxt->Des(), KUpdateBitmap ); - WriteUpdateBitmapL( restarttxt->Des(), KRestartingBitmap ); - delete updatetxt; - delete restarttxt; - - // Simulate update agent by writing result file. - CRepository* centrep(NULL); - TInt err = KErrNone; - TRAP(err, centrep = CRepository::NewL( KCRUidFotaServer ) ); - TInt simulate(KErrNotFound); - if (centrep) - { - err = centrep->Get(KSimulateUpdateAgent, simulate); - } - delete centrep; - if (simulate > 0) - { - FLOG(_L("CFotaUpdate::UpdateL 5 - writing update.resp")); - RFileWriteStream respstr; - CleanupClosePushL(respstr); - User::LeaveIfError(respstr.Replace(iFotaServer->iFs, - KUpdateResultFile, EFileWrite)); - - respstr.WriteUint32L(UPD_OK); - respstr.WriteUint32L(15); - respstr.WriteL(_L("UPDATE DONE!")); - CleanupStack::PopAndDestroy(&respstr); - } - - iFotaServer->SetStartupReason(EFotaDefault); - - RStarterSession starter; - FLOG(_L(" starter->Connect")); - User::LeaveIfError(starter.Connect()); - starter.Reset(RStarterSession::EFirmwareUpdate); - starter.Close(); - FLOG(_L("CFotaUpdate::UpdateL() <<")); - } - -// --------------------------------------------------------------------------- -// CFotaUpdate::CheckBatteryL() -// Cheks if there's enough battery power to update -// --------------------------------------------------------------------------- -// -TBool CFotaUpdate::CheckBatteryL() - { - FLOG(_L("CFotaUpdate::CheckBatteryL >>")); - - TInt chargingstatus(EChargingStatusError); - TInt batterylevel(EBatteryLevelUnknown); - TBool enoughPower(EFalse); - - // Read battery level - - RProperty pw; - User::LeaveIfError(pw.Attach(KPSUidHWRMPowerState, KHWRMBatteryLevel)); - User::LeaveIfError(pw.Get(batterylevel)); - - if (batterylevel >= BatteryLevelAccepted) - { - FLOG(_L("Battery charge is above acceptable level!")); - enoughPower = ETrue; - } - else - { - - //Read charger status - User::LeaveIfError(pw.Attach(KPSUidHWRMPowerState, - KHWRMChargingStatus)); - User::LeaveIfError(pw.Get(chargingstatus)); - pw.Close(); - - // But charger is connected, power sufficient - if (chargingstatus == EChargingStatusCharging || chargingstatus - == EChargingStatusAlmostComplete || chargingstatus - == EChargingStatusChargingComplete || chargingstatus - == EChargingStatusChargingContinued) - { - FLOG( - _L("Battery charge is below acceptable level, but charger is connected!")); - enoughPower = ETrue; - } - } - - FLOG(_L("CFotaUpdate::CheckBattery, current charge = %d, ret = %d <<"), - batterylevel, enoughPower); - return enoughPower; - } - -void CFotaUpdate::MonitorBatteryChargeLevel() - { - FLOG(_L("CFotaUpdate::MonitorBatteryChargeLevel >>")); - - CancelMonitor(); - - iProperty.Attach(KPSUidHWRMPowerState, KHWRMBatteryLevel); - TInt value = 0; - - iProperty.Get(KPSUidHWRMPowerState, KHWRMBatteryLevel, value); - - FLOG(_L("Battery level at this time is %d, err = %d"), value); - iStatus = KRequestPending; - iProperty.Subscribe(iStatus); - - iMonitorType = BatteryLevel; - SetActive(); - - FLOG(_L("CFotaUpdate::MonitorBatteryChargeLevel <<")); - } - -void CFotaUpdate::MonitorBatteryChargingStatus() - { - FLOG(_L("CFotaUpdate::MonitorBatteryChargingStatus >>")); - - CancelMonitor(); - - iProperty.Attach(KPSUidHWRMPowerState, KHWRMChargingStatus); - TInt value = 0; - - iProperty.Get(KPSUidHWRMPowerState, KHWRMChargingStatus, value); - - FLOG(_L("Charging status at this time is %d, err = %d"), value); - iStatus = KRequestPending; - iProperty.Subscribe(iStatus); - - iMonitorType = ChargingStatus; - SetActive(); - - FLOG(_L("CFotaUpdate::MonitorBatteryChargingStatus <<")); - } - -void CFotaUpdate::CancelMonitor() - { - FLOG(_L("CFotaUpdate::CancelMonitor >>")); - if (IsActive()) - { - FLOG(_L("Cancelling....")); - Cancel(); - } - FLOG(_L("CFotaUpdate::CancelMonitor <<")); - } - -TBool CFotaUpdate::IsUSBConnected() - { - FLOG(_L("CFotaUpdate::IsUSBConnected >>")); - - TBool ret (EFalse); - TUsbDeviceState state(EUsbDeviceStateUndefined); - RUsb usbman; - TInt err = usbman.Connect(); - if (err == KErrNone) - { - usbman.GetDeviceState(state); - usbman.Close(); - } - if (state != EUsbDeviceStateUndefined) - { - ret = ETrue; - } - - FLOG(_L("CFotaUpdate::IsUSBConnected, value = %d, ret = %d <<"), state, ret); - return ret; - } - -void CFotaUpdate::RunL() - { - FLOG(_L("CFotaUpdate::RunL >>")); - - if (iStatus.Int() == KErrNone) - { - TInt value = 0; - - if (iMonitorType == BatteryLevel) - { - iProperty.Get(KPSUidHWRMPowerState, KHWRMBatteryLevel, - value); - - FLOG(_L("Battery level has changed to %d"), value); - - iFotaServer->UpdateBatteryLowInfo( - (value >= BatteryLevelAccepted) ? EFalse : ETrue); - - MonitorBatteryChargeLevel(); - } - else if (iMonitorType == ChargingStatus) - { - iProperty.Get(KPSUidHWRMPowerState, KHWRMChargingStatus, - value); - - FLOG(_L("Charging status has changed to %d"), value); - - if (value == EChargingStatusCharging || value - == EChargingStatusAlmostComplete || value - == EChargingStatusChargingComplete || value - == EChargingStatusChargingContinued) - { - if (IsUSBConnected()) - { - ShowDialogL(EFwUpdNotEnoughBattery); - } - else - { - iFotaServer->UpdateBatteryLowInfo(EFalse); - } - } - else - { - iFotaServer->UpdateBatteryLowInfo(ETrue); - } - } - - } - FLOG(_L("CFotaUpdate::RunL, iStatus = %d <<"), iStatus.Int()); - } - -// --------------------------------------------------------------------------- -// CFotaUpdate::StartUpdateL -// Starts fw updating (shows a notifier to user). -// --------------------------------------------------------------------------- -// -void CFotaUpdate::StartUpdateL(const TDownloadIPCParams &aParams) - { - FLOG(_L("CFotaUpdate::StartUpdateL, pkig:%d >>"), aParams.iPkgId); - - //First cancel any ongoing battery monitoring. - CancelMonitor(); - - UpdateL(); - - FLOG(_L("CFotaUpdate::StartUpdateL <<")); - } - -TInt CFotaUpdate::RunError(TInt aError) - { - FLOG(_L("CFotaUpdate::RunError, error = %d >>"), aError); - return aError; - } - -void CFotaUpdate::DoCancel() - { - FLOG(_L("CFotaUpdate::DoCancel >>")); - - iProperty.Cancel(); - - FLOG(_L("CFotaUpdate::DoCancel <<")); - } - -void CFotaUpdate::ShowDialogL(TFwUpdNoteTypes aDialogid) - { - FLOG(_L("CFotaUpdate::ShowDialogL, dialogid = %d >>"), aDialogid); - iFotaServer->ServerCanShut(EFalse); - - if (iFotaServer->FullScreenDialog()) - iFotaServer->FullScreenDialog()->Close(); - - iNotifParams = CHbSymbianVariantMap::NewL(); - - HBufC* keyDialog = HBufC::NewL(10); - CleanupStack::PushL(keyDialog); - *keyDialog = KKeyDialog; - - CHbSymbianVariant* dialogId = CHbSymbianVariant::NewL(&aDialogid, - CHbSymbianVariant::EInt); - iNotifParams->Add(*keyDialog, dialogId); - iNotifier = CFotaDownloadNotifHandler::NewL(this); - - iNotifier->LaunchNotifierL(iNotifParams, aDialogid); - - CleanupStack::PopAndDestroy(); - FLOG(_L("CFotaUpdate::ShowDialogL <<")); - } - -void CFotaUpdate::HandleDialogResponse(int response, TInt aDialogId) - { - FLOG(_L("CFotaUpdate::HandleDialogResponse, dialogid = %d response = %d >>"), aDialogId, response); - - if (aDialogId == EFwUpdNotEnoughBattery) - { - iFotaServer->FinalizeUpdate(); - } - - FLOG(_L("CFotaUpdate::HandleDialogResponse <<")); - } - -TInt CFotaUpdate::WriteUpdateBitmapL( const TDesC& aText, const TDesC& aFile) - { - FLOG(_L("WriteUpdateBitmapL writing %S to %S w/ txtdir"),&aText,&aFile); - - TSize screensize = CCoeEnv::Static()->ScreenDevice()->SizeInPixels(); - TInt width = screensize.iWidth - KBmpMargin*2; - TInt height = screensize.iHeight; - - CArrayFixSeg* lines = new CArrayFixSeg(5); - CleanupStack::PushL(lines); - CFbsBitmap* bitmap = new ( ELeave ) CFbsBitmap; - CleanupStack::PushL( bitmap ); - bitmap->Create( TSize(width,height), EColor64K ); - CFbsBitmapDevice* device = CFbsBitmapDevice::NewL( bitmap ); - CleanupStack::PushL( device ); - const CFont* font = AknLayoutUtils::FontFromId(EAknLogicalFontPrimaryFont); - CFbsBitGc* context; - User::LeaveIfError( device->CreateContext( context ) ); - CleanupStack::PushL( context ); - TInt ascent = font->AscentInPixels(); - TInt descent = font->DescentInPixels(); - context->UseFont ( font ); - context->Clear(); // bg color - - // Visually ordered text - HBufC* wrappedstring = AknBidiTextUtils::ConvertToVisualAndWrapToArrayL( - aText, width,*font, *lines); - CleanupStack::PushL ( wrappedstring ); - TBool dirfound (ETrue); - // direction of text, affects alignemnt - TBidiText::TDirectionality direction = TBidiText::TextDirectionality( - *wrappedstring, &dirfound ); - - // Print visual text to bitmap - for ( TInt i=0; iCount(); ++i ) - { - TPtrC l = (*lines)[i]; - TInt top = (ascent+descent)*(i); - TInt bot = (ascent+descent)*(i+1); - TRect rect (0, top ,width, bot ); - CGraphicsContext::TTextAlign alignment = - direction==TBidiText::ELeftToRight ? CGraphicsContext::ELeft - : CGraphicsContext::ERight; - context->DrawText(l, rect, ascent, alignment); - } - height = (ascent+descent)*lines->Count() + descent; - bitmap->Resize( TSize(width,height)); - bitmap->Save( aFile ); - context->DiscardFont(); - CleanupStack::PopAndDestroy( wrappedstring ); - CleanupStack::PopAndDestroy( context ); - CleanupStack::PopAndDestroy( device ); - CleanupStack::PopAndDestroy( bitmap ); - CleanupStack::PopAndDestroy( lines ); - return 1; - }