diff -r 185201be11b0 -r 516af714ebb4 memspy/Engine/Source/ThreadAndProcess/MemSpyEngineObjectProcess.cpp --- a/memspy/Engine/Source/ThreadAndProcess/MemSpyEngineObjectProcess.cpp Thu Sep 02 22:05:40 2010 +0300 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,651 +0,0 @@ -/* -* Copyright (c) 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 - -// System includes -#include -#include - -// Driver includes -#include -#include // for terminate - -// User includes -#include -#include -#include - -// Literal constants -_LIT( KMemSpyUnknownProcessName, "Unknown" ); -_LIT( KMemSpyUnknownExitCategory, "Unknown ExitCat" ); -_LIT( KMemSpyStandardProcessExtension, ".exe" ); - - -CMemSpyProcess::CMemSpyProcess( TProcessId aId, CMemSpyEngine& aEngine ) -: iId( aId ), iEngine( aEngine ) - { - } - - -CMemSpyProcess::~CMemSpyProcess() - { -#ifdef _DEBUG - if ( iName != NULL ) - { - RDebug::Print(_L( "MEMSPY - dtor - CMemSpyProcess() - this: 0x%08x, name: %S"), this, iName); - } - else - { - RDebug::Printf( "MEMSPY - dtor - CMemSpyProcess() - this: 0x%08x", this ); - } -#endif - - CloseAllThreads(); - iThreads.Close(); - delete iName; - delete iInfo; - } - - -void CMemSpyProcess::ConstructL() - { - iInfo = new(ELeave) TMemSpyDriverProcessInfo(); - - RMemSpyDriverClient& driver = iEngine.Driver(); - RProcess process; - User::LeaveIfError( driver.OpenProcess( iId, process ) ); - CleanupClosePushL( process ); - - // Find the threads before we start tinkering with the process - // name - LocateThreadsL( process ); - - // Now build the process name - RefreshL( process ); - - CleanupStack::PopAndDestroy( &process ); - - -#ifdef _DEBUG - if ( iName != NULL ) - { - RDebug::Print(_L( "MEMSPY - ctor - CMemSpyProcess() - this: 0x%08x, name: %S"), this, iName); - } - else - { - RDebug::Printf( "MEMSPY - ctor - CMemSpyProcess() - this: 0x%08x", this ); - } -#endif - } - - -EXPORT_C CMemSpyProcess* CMemSpyProcess::NewL( const CMemSpyProcess& aCopyMe ) - { - CMemSpyProcess* self = NewL( aCopyMe.Id(), aCopyMe.iEngine ); - return self; - } - - -CMemSpyProcess* CMemSpyProcess::NewL( TProcessId aId, CMemSpyEngine& aEngine ) - { - CMemSpyProcess* self = CMemSpyProcess::NewL( aId, aEngine ); - CleanupStack::Pop( self ); - return self; - } - - -CMemSpyProcess* CMemSpyProcess::NewLC( TProcessId aId, CMemSpyEngine& aEngine ) - { - CMemSpyProcess* self = new(ELeave) CMemSpyProcess( aId, aEngine ); - CleanupClosePushL( *self ); - self->ConstructL(); - return self; - } - - -EXPORT_C void CMemSpyProcess::Close() - { - if ( !OpenOrCloseInProgress() ) - { - const TInt ac = AccessCount(); - SetOpenOrCloseInProgress( ETrue ); - - // Calling close can do a "delete this" so make sure - // we don't try to access the object again in that situation... - CMemSpyEngineObject::Close(); - if ( ac - 1 > 0 ) - { - SetOpenOrCloseInProgress( EFalse ); - } - else - { - // We don't care - we've just been deleted! - } - } - } - - -EXPORT_C void CMemSpyProcess::Open() - { - if ( !OpenOrCloseInProgress() ) - { - SetOpenOrCloseInProgress( ETrue ); - CMemSpyEngineObject::Open(); - SetOpenOrCloseInProgress( EFalse ); - } - } - - -EXPORT_C TInt CMemSpyProcess::MdcaCount() const - { - return iThreads.Count(); - } - - -EXPORT_C TPtrC CMemSpyProcess::MdcaPoint(TInt aIndex) const - { - const CMemSpyThread* thread = iThreads[ aIndex ]; - return TPtrC( thread->NameForListBox() ); - } - - -EXPORT_C TInt CMemSpyProcess::ThreadIndexById( TThreadId aId ) const - { - TInt index = KErrNotFound; - // - const TInt count = iThreads.Count(); - for( TInt i=0; iId() == aId ) - { - index = i; - break; - } - } - // - return index; - } - - -EXPORT_C CMemSpyThread& CMemSpyProcess::ThreadByIdL( TThreadId aId ) const - { - CMemSpyThread* ret = NULL; - // - const TInt count = iThreads.Count(); - for( TInt i=0; iId() == aId ) - { - ret = thread; - break; - } - } - // - if ( ret == NULL ) - { - User::Leave( KErrNotFound ); - } - // - return *ret; - } - - - -EXPORT_C TPtrC CMemSpyProcess::Name() const - { - // Just return the pure name, minus the leading tab - TPtrC pRet( iName->Mid(2) ); - - // Find the last tab position - TInt pos = pRet.Locate(TChar('\t')); - if ( pos > 0 ) - { - pRet.Set( pRet.Left( pos ) ); - } - // - return pRet; - } - - -EXPORT_C CMemSpyThread& CMemSpyProcess::At( TInt aIndex ) const - { - CMemSpyThread* ret = iThreads[ aIndex ]; - return *ret; - } - - -EXPORT_C void CMemSpyProcess::TerminateL() - { - RMemSpyDriverClient& driver = iEngine.Driver(); - RProcess process; - User::LeaveIfError( driver.OpenProcess( iId, process ) ); - process.Terminate( EPanicForcedTerminate ); - process.Close(); - // - RefreshL(); - } - - -EXPORT_C void CMemSpyProcess::KillL() - { - RMemSpyDriverClient& driver = iEngine.Driver(); - RProcess process; - User::LeaveIfError( driver.OpenProcess( iId, process ) ); - process.Kill( EPanicForcedKill ); - process.Close(); - // - RefreshL(); - } - - -EXPORT_C void CMemSpyProcess::PanicL() - { - RMemSpyDriverClient& driver = iEngine.Driver(); - RProcess process; - User::LeaveIfError( driver.OpenProcess( iId, process ) ); - process.Panic( KMemSpyClientPanic, EPanicForcedPanic ); - process.Close(); - // - RefreshL(); - } - - -EXPORT_C TBool CMemSpyProcess::IsSystemPermanent() const - { - const TBool ret = ( iInfo->iFlags & KProcessFlagSystemPermanent ); - return ret; - } - - -EXPORT_C TBool CMemSpyProcess::IsSystemCritical() const - { - const TBool ret = ( iInfo->iFlags & KProcessFlagSystemCritical ); - return ret; - } - - -void CMemSpyProcess::LocateThreadsL( RProcess& aProcess ) - { - __ASSERT_ALWAYS( aProcess.Handle() != KNullHandle, MemSpyEngineUtils::Panic( EMemSpyEnginePanicProcessHandleNullWhenAttemptingToIdentifyThreads ) ); - -#ifdef _DEBUG - RDebug::Printf("CMemSpyProcess::LocateThreadsL() - START - this: 0x%08x, pid: %d (0x%04x)", this, (TUint) aProcess.Id(), (TUint) aProcess.Id() ); -#endif - - RArray threadIds; - CleanupClosePushL( threadIds ); - - // Get list of child threads from driver. - iEngine.Driver().GetThreadsL( aProcess.Id(), threadIds ); - - // Create therad object for each thread the driver returned to us... - const TInt count = threadIds.Count(); -#ifdef _DEBUG - RDebug::Printf("CMemSpyProcess::LocateThreadsL() - got %d threads", count ); -#endif - - for( TInt i=0; i priority; - AppendPriority( priority, iPriority ); - - // Convert the full name to the format we want in the UI - TBuf name; - TMemSpyTruncateOverflow overflow; - - // FOR ALIVE PROCESSES: - // - // 1] Space, followed by tab - // 2] Process name (minus .exe) - // 3] Tab, Tab - // 4] Process uid - // 5] Thread count - // 6] Process priority - // - // FOR DEAD PROCESSES: - // - // 1] Space, followed by tab - // 2] Process name (minus .exe) - // 3] Tab, Tab - // 4] Process uid - // 5] Exit info - - // Common - _LIT( KMemSpyProcessNameFormatSpecBasicName, " \t%S\t\t%8x, " ); - name.AppendFormat( KMemSpyProcessNameFormatSpecBasicName, &overflow, rawProcessName, iInfo->SID() ); - CleanupStack::PopAndDestroy( rawProcessName ); - - if ( IsDead() ) - { - CMemSpyThread::AppendExitInfo( name, iExitType, iExitReason, iExitCategory ); - } - else - { - _LIT( KMemSpyProcessNameFormatSpecAlive, "%2d thr, %S" ); - name.AppendFormat( KMemSpyProcessNameFormatSpecAlive, &overflow, iThreads.Count(), &priority ); - } - - // Save end result - HBufC* finalName = name.AllocL(); - delete iName; - iName = finalName; - } - - -void CMemSpyProcess::SetDeadL() - { - RefreshL(); - } - - -void CMemSpyProcess::SetDeadL( const RProcess& aProcess ) - { - RefreshL( aProcess ); - } - - -EXPORT_C TBool CMemSpyProcess::IsDead() const - { - const TBool isDead = ( iExitType != EExitPending ); - return isDead; - } - - -EXPORT_C TUint32 CMemSpyProcess::SID() const - { - return iInfo->SID(); - } - - -EXPORT_C TUint32 CMemSpyProcess::VID() const - { - return iInfo->VID(); - } - -EXPORT_C TProcessPriority CMemSpyProcess::Priority() const - { - return iPriority; - } - -EXPORT_C TExitCategoryName CMemSpyProcess::ExitCategory() const - { - return iExitCategory; - } - -EXPORT_C TInt CMemSpyProcess::ExitReason() const - { - return iExitReason; - } - -EXPORT_C TExitType CMemSpyProcess::ExitType() const - { - return iExitType; - } - -EXPORT_C TUidType CMemSpyProcess::UIDs() const - { - return iInfo->iUids; - } - - -EXPORT_C SCapabilitySet CMemSpyProcess::Capabilities() const - { - return iInfo->iSecurityInfo.iCaps; - } - -void CMemSpyProcess::FullName( TDes& aFullName ) const - { - // c32exe.exe[101f7989]0001 - aFullName.Zero(); - aFullName.Append( Name() ); - if ( iFlags & EFlagsIncludedExecutableWithinName ) - { - // Add .exe - aFullName.Append( KMemSpyStandardProcessExtension ); - } - - aFullName.Append( '[' ); - aFullName.AppendNumFixedWidth( iInfo->iUids[ 2 ].iUid, EHex, 8 ); - aFullName.Append( ']' ); - aFullName.AppendNumFixedWidth( iInfo->iGeneration, EDecimal, 4 ); - } - - -void CMemSpyProcess::HandleThreadIsBornL( const TThreadId& aId ) - { - // A new thread has been created in this process. Just in case, we'll - // check there isn't already an existing thread with the same id... - const TInt index = ThreadIndexById( aId ); - if ( index < 0 ) - { - TRAP_IGNORE( - CMemSpyThread* threadObj = CMemSpyThread::NewLC( aId, *this ); - iThreads.AppendL( threadObj ); - CleanupStack::Pop( threadObj ); - ); - } - } - - -HBufC* CMemSpyProcess::GetProcessNameLC( const RProcess& aProcessOrNull, TBool& aProcessNameIncludesExeSuffix ) const - { - _LIT( KMemSpySquareBraceOpen, "[" ); - // - TFullName processName; - - // Assume the flags have already been set once previously in order to form default response - aProcessNameIncludesExeSuffix = ( iFlags & EFlagsIncludedExecutableWithinName ); - - const TBool handleValid = aProcessOrNull.Handle() != KNullHandle; - if ( handleValid ) - { - // Easy case - we have a valid thread handle... - // - // Get full name, e.g.: - // - // c32exe.exe[101f7989]0001 - aProcessOrNull.FullName( processName ); - - // ... but we need to clean up the name so that it - // doesn't include the process UID, and neither does it - // include the extension (.exe). - TInt pos = processName.FindF( KMemSpySquareBraceOpen ); - if ( pos > 0 ) - { - processName.SetLength( pos ); - } - - // Discard '.exe' - pos = processName.FindF( KMemSpyStandardProcessExtension ); - if ( pos > 0 ) - { - aProcessNameIncludesExeSuffix = ETrue; - processName.SetLength( pos ); - } - } - else - { - // Since we don't have the possibility to enquire after the process's name - // we'll assume that it used to be alive and therefore at some point we did - // manage to grep it's name... - if ( iName ) - { - const TPtrC pOriginalName( Name() ); - processName.Append( pOriginalName ); - } - else - { - // Don't have a process handle, don't have any possibility to get the - // name from a prior cached version. Must use "unknown" - processName.Append( KMemSpyUnknownProcessName ); - } - } - // - HBufC* ret = processName.AllocLC(); - return ret; - } - - -void CMemSpyProcess::CloseAllThreads() - { - const TInt count = iThreads.Count(); - for(TInt i=count-1; i>=0; i--) - { - CMemSpyThread* thread = iThreads[ i ]; - thread->Close(); - } - } -