diff -r 000000000000 -r af10295192d8 linklayerprotocols/pppnif/SPPP/PPPLRD.CPP --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/linklayerprotocols/pppnif/SPPP/PPPLRD.CPP Tue Jan 26 15:23:49 2010 +0200 @@ -0,0 +1,204 @@ +// Copyright (c) 1997-2009 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: +// + +#include +#include +#include "PPPLRD.H" +#include "PPPLOG.H" +#include "PPPLCP.H" +#include "PPPBASE.H" + +// +CPppLrd::CPppLrd(CPppLcp* aPppLcp):iPppLcp(aPppLcp) + {} + +CPppLrd::~CPppLrd() + { + TimerCancel(); + TimerDelete(); + } + +CPppLrd* CPppLrd::NewL(CPppLcp* aPppLcp) +/** +Create a new object instance. + +@return Pointer to new object +*/ + { + CPppLrd* self=new (ELeave)CPppLrd(aPppLcp); + CleanupStack::PushL(self); + self->ConstructL(); + CleanupStack::Pop(); + return self; + } + +void CPppLrd::ConstructL() +/** +Initialize the object and start the timer. +*/ + { + iShiftRegister = KShiftRegisterWidth; + iBitCount = KSampleWidth; + TimerConstructL(KPppLrdTimerPriority); + // Initialise with default value + iPppLrdEnabled = KPppLrdDefaultEnabledMode; + iLrdPeriod = KPppLrdDefaultTimerPeriod; + // Override default with values from INI file + ReadIniFileL(); + StartTimer(); + } + +void CPppLrd::ReadIniFileL() +/** +Read the LRD section of the ppp.ini file. +*/ + { + CESockIniData* ini = NULL; + TRAPD(res, + if (iPppLcp->PppLinkMode() == CPppLcpConfig::EPppLinkIsServer) + { + ini = CESockIniData::NewL(PPP_SERVER_INI_FILE); + } + else + { + ini = CESockIniData::NewL(PPP_INI_FILE); + } + ) + if(res!=KErrNone) + { + if(res==KErrNotFound) + return; + User::Leave(res); + } + CleanupStack::PushL(ini); + TInt entry = 0; + // Read enable switch + if (ini->FindVar(LRDSECTIONNAME,LRDENTRYNAME_ENABLE, entry)) + { + if (entry == 0) + iPppLrdEnabled = EFalse; + else + iPppLrdEnabled = ETrue; + } + // Read period value + if (ini->FindVar(LRDSECTIONNAME,LRDENTRYNAME_PERIOD, entry)) + { + if((entry >= KPppLrdTimerPeriodMin) && (entry <=KPppLrdTimerPeriodMax)) + iLrdPeriod = entry; + } + + CleanupStack::PopAndDestroy(); + } + +void CPppLrd::StartTimer() +/** +Start the timer. +*/ + { + if(iPppLrdEnabled) + { + iLastEchoAck = ETrue; + TimerAfter(iLrdPeriod*1000000); + } + } + +void CPppLrd::StopTimer() +/** +Stop the timer. +*/ + { + TimerCancel(); + } + +void CPppLrd::RecvEchoReply(TUint8 aIdentifier) +/** +Upcall from LCP when an Echo Reply packet is received. + +@param aIdentifier Packet identifier +*/ + { + // Check this reply matches the last request + iLastEchoAck = (iLastEchoAck || (iEchoReqFrameIdentifier == aIdentifier)); + LOG( iPppLcp->iLogger->Printf(_L("CPppLrd::RecvEchoReply "));) + if(iLastEchoAck) + {LOG( iPppLcp->iLogger->Printf(_L("TRUE\n"));)} + else + {LOG( iPppLcp->iLogger->Printf(_L("FALSE\n"));)} + } + +void CPppLrd::TimerComplete(TInt /*aStatus*/) +/** +Checks how many Echo Reply packets we've received and shuts down the link +if we've missed too many. If we're still OK, send another Echo Request. +Called by MTimer on timer expiry. + +@param aStatus Aynchronous request completion status (ignored) +*/ + { + // Shift Register + iShiftRegister <<=1; + // Update Bit counter + iBitCount -= (iShiftRegister & KBitOverflow ? 1:0); + // Update Register with last answer + iShiftRegister |=(iLastEchoAck?1:0); + // Update Bit counter + iBitCount += (iLastEchoAck?1:0); + LOG( iPppLcp->iLogger->Printf(_L("CPppLrd::TimerComplete \n")); ) + // Check the number of missed echo answers + if(iBitCount == (KSampleWidth-KMaxNFailure)) + { + // too many missed replies - we're dead + // signal that to the PPP stack + // with code below? - Check that 1st + // Changed Error Code to reflect faulty transmission chain + iPppLcp->Stop(KErrIfLRDBadLine,MNifIfNotify::EDisconnect); + LOG( iPppLcp->iLogger->Printf(_L("Lrd detected a link FAILURE\nDropping the connection\n")); ) + return; + } + // Otherwise if we're opened carry on sending echo request + if(iPppLcp->FsmIsThisLayerOpen()) + iEchoReqFrameIdentifier = iPppLcp->SendEchoRequest(); + else + iEchoReqFrameIdentifier = 0; + if(iEchoReqFrameIdentifier) + iLastEchoAck = EFalse; + else + // if for some reason sending the echo req failed + // disable decrementing the counter + // We still trigger the timer and retry later on + iLastEchoAck = ETrue; + TimerAfter(iLrdPeriod*1000000); + } + +void CPppLrd::EnableOrDisableTimer(TBool aEnable) +/** +Leave enabled or disable the echo check by starting or stopping the timer. +If the timer is stopped, it will not be restarted by this method. + +@param aEnable EFalse to stop the timer +*/ + { + if (!aEnable) + { + StopTimer(); + iPppLrdEnabled=EFalse; + } + else + { + iPppLrdEnabled=ETrue; + // TODO: do we need to reset anything here? + } + } +