kernel/eka/drivers/debug/rmdebug/d_rmd_breakpoints.h
changeset 245 647ab20fee2e
parent 244 a77889bee936
child 252 0a40b8675b23
equal deleted inserted replaced
244:a77889bee936 245:647ab20fee2e
     1 // Copyright (c) 2004-2010 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 the License "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 // Refactored class containing breakpoint related code from rm_debug_kerneldriver.cpp
       
    15 //
       
    16 
       
    17 
       
    18 
       
    19 /**
       
    20  @file
       
    21  @internalComponent
       
    22  @released
       
    23 */
       
    24 
       
    25 #ifndef D_RMD_BREAKPOINTS_H
       
    26 #define D_RMD_BREAKPOINTS_H
       
    27 
       
    28 #include <rm_debug_api.h>
       
    29 #include <kernel/kern_priv.h>
       
    30 #include "rm_debug_kerneldriver.h"
       
    31 
       
    32 // fwd declaration of friend classes needed due to re-factoring
       
    33 class DRM_DebugChannel;
       
    34 
       
    35 class DRMDStepper;
       
    36 
       
    37 //
       
    38 // Macros
       
    39 //
       
    40 const TUint32 KArmBreakPoint = 0xE7F123F4;
       
    41 const TUint16 KThumbBreakPoint = 0xDE56;
       
    42 const TUint16 KT2EEBreakPoint = 0xC100;	// From ARM ARM DDI0406A, section A9.2.1 Undefined instruction encoding for Thumb2-EE.
       
    43 
       
    44 #define NUMBER_OF_TEMP_BREAKPOINTS 10
       
    45 
       
    46 #define NUMBER_OF_MAX_BREAKPOINTS 100
       
    47 
       
    48 //
       
    49 // class TBreakEntry
       
    50 //
       
    51 class TBreakEntry
       
    52 {
       
    53 public:
       
    54 
       
    55 	inline TBreakEntry() { Reset(); };
       
    56 
       
    57 	inline TBreakEntry(Debug::TBreakId aBreakId, TUint64 aId, TBool aThreadSpecific, TUint32 aAddress, Debug::TArchitectureMode aMode)
       
    58 			: iBreakId(aBreakId),
       
    59 			  iId(aId),
       
    60 			  iAddress(aAddress),
       
    61 			  iMode(aMode),
       
    62 			  iThreadSpecific(aThreadSpecific)
       
    63 	{
       
    64 		 iInstruction.FillZ(4);
       
    65 		 iPageAddress = 0;
       
    66 		 iDisabledForStep = EFalse;
       
    67 		 iObsoleteLibraryBreakpoint = EFalse;
       
    68 		 iResumeOnceOutOfRange = EFalse;
       
    69 		 iSteppingInto = EFalse;
       
    70 		 iRangeStart = 0;
       
    71 		 iRangeEnd = 0;
       
    72 		 iStepTarget = EFalse;
       
    73 		 iNumSteps = 0;
       
    74 	};
       
    75 	
       
    76 	inline void Reset()
       
    77 	{
       
    78 		 iId = 0;
       
    79 		 iAddress = 0;
       
    80 		 iMode = Debug::EArmMode;
       
    81 		 iInstruction.FillZ(4);
       
    82 		 iPageAddress = 0;
       
    83 		 iDisabledForStep = EFalse;
       
    84 		 iObsoleteLibraryBreakpoint = EFalse;
       
    85 		 iResumeOnceOutOfRange = EFalse;
       
    86 		 iSteppingInto = EFalse;
       
    87 		 iRangeStart = 0;
       
    88 		 iRangeEnd = 0;
       
    89 		 iStepTarget = EFalse;
       
    90 		 iNumSteps = 0;
       
    91 	};
       
    92 
       
    93 public:
       
    94 	// Unique Id for this breakpoint. Assigned by D_RMD_Breakpoints::DoSetBreak(). @see D_RMD_Breakpoints::DoSetBreak
       
    95 	TInt32		iBreakId;
       
    96 	// Consider making the iId into a union of TProcessId, TThreadId, global etc. to make things more obvious
       
    97 	// Object Id in which this breakpoint should operate.
       
    98 	TUint64		iId;
       
    99 	// Address at which this breakpoint should operate
       
   100 	TUint32		iAddress;
       
   101 	// CPU ISA which this breakpoint uses, e.g. EArmMode/EThumbMode.
       
   102 	Debug::TArchitectureMode iMode;
       
   103 	// The original instruction which was stored at iAddress.
       
   104 	TBuf8<4>	iInstruction;
       
   105 	TUint32		iPageAddress;   //not used: BC if we remove it
       
   106 
       
   107 	// Indicates whether this breakpoint has been temporarily replaced with original instruction to enable step-off this breakpoint
       
   108 	TBool		iDisabledForStep;
       
   109 	/* This is used when libraries and processes are removed, so that
       
   110 	 * the driver can say 'ok' when requested to remove breakpoints
       
   111 	 * that existed in these cases, rather than 'Not Found'.
       
   112 	 *
       
   113 	 * Its not logical, but its a BC break if we change it :-(
       
   114 	 */
       
   115 	TBool		iObsoleteLibraryBreakpoint;
       
   116 	// Indicates whether this thread should be resumed after stepping off this breakpoint
       
   117 	TBool		iResumeOnceOutOfRange;
       
   118 	TBool		iSteppingInto;
       
   119 	TUint32		iRangeStart;
       
   120 	TUint32		iRangeEnd;
       
   121 	TBool		iThreadSpecific;
       
   122 	TBool		iStepTarget;
       
   123 
       
   124 	// Indicates how many more instruction steps should occur after hitting this breakpoint
       
   125 	TInt		iNumSteps;
       
   126 };
       
   127 /**
       
   128 @internalTechnology
       
   129 
       
   130 This class encapsulates all the data concerning run-mode and stop mode breakpoints
       
   131 as understood by the run-mode and stop-mode debug system.
       
   132 
       
   133 Note:                                                                        
       
   134 	The internal list of breakpoints is currently divided into two sections. The range from
       
   135 	0...NUMBER_OF_TEMP_BREAKPOINTS is used internally by the debug driver for implementing
       
   136 	stepping. The range from NUMBER_OF_TEMP_BREAKPOINTS to NUMBER_OF_MAX_BREAKPOINTS is used
       
   137 	to store information about breakpoints set by the client debug agents.
       
   138                                                                                                                                                             
       
   139 	In future, this should change, so that each breakpoint knows what kind of breakpoint it
       
   140 	is (user/temp etc).
       
   141 
       
   142 
       
   143 */
       
   144 class D_RMD_Breakpoints : public DBase
       
   145 {
       
   146 public:
       
   147 	D_RMD_Breakpoints(DRM_DebugChannel* aChannel);
       
   148 	~D_RMD_Breakpoints();
       
   149 
       
   150 	TInt Init();
       
   151 
       
   152 	// from rm_debug_driver.h
       
   153 	TInt DoSetBreak(TInt32 &aBreakId, const TUint64 aId, const TBool aThreadSpecific, const TUint32 aAddress, const Debug::TArchitectureMode aMode );
       
   154 	TInt DoEnableBreak(TBreakEntry &aEntry, TBool aSaveOldInstruction);
       
   155 	TInt DoClearBreak(const TInt32 aBreakId, TBool aIgnoreTerminatedThreads=EFalse);
       
   156 	TInt DoModifyBreak(TModifyBreakInfo* aBreakInfo);
       
   157 	TInt DoModifyProcessBreak(TModifyProcessBreakInfo* aBreakInfo);
       
   158 	TInt DoBreakInfo(TGetBreakInfo* aBreakInfo);
       
   159 	void ClearAllBreakPoints();
       
   160 	TInt DisableBreakAtAddress(TUint32 aAddress);
       
   161 	TInt DoEnableDisabledBreak(TUint64 aThreadId);
       
   162 
       
   163 	void DoRemoveThreadBreaks(TUint64 aThreadId);
       
   164 	void RemoveBreaksForProcess(TUint64 aProcessId, TUint32 aCodeAddress, TUint32 aCodeSize);
       
   165 	void InvalidateLibraryBreakPoints(TUint32 aCodeAddress, TUint32 aCodeSize);
       
   166 	TInt BreakPointCount() const;
       
   167 	TBreakEntry* GetNextBreak(const TBreakEntry* aBreakEntry) const;
       
   168 	TBool IsTemporaryBreak(const TBreakEntry& aBreakEntry) const;
       
   169 
       
   170 	TInt DoGetBreakList(TUint32* aBuffer, const TUint32 aBufSize, const TUint32 aElement, TUint32& aLastElement);
       
   171 
       
   172 	// Useful helper functions for debugging breakpoint issues
       
   173 	inline void print_BreakpointsDisabledForStep();
       
   174 	inline void print_BreakpointsList();
       
   175 
       
   176 private:
       
   177 	// Locked versions of public functions
       
   178 	TInt priv_DoSetBreak(TInt32 &aBreakId, const TUint64 aId,  const TBool aThreadSpecific, const TUint32 aAddress, const Debug::TArchitectureMode aMode );
       
   179 	TInt priv_DoEnableBreak(TBreakEntry &aEntry, TBool aSaveOldInstruction);
       
   180 	TInt priv_DoClearBreak(const TInt32 aBreakId, TBool aIgnoreTerminatedThreads);
       
   181 	TInt priv_DoModifyBreak(TModifyBreakInfo* aBreakInfo);
       
   182 	TInt priv_DoModifyProcessBreak(TModifyProcessBreakInfo* aBreakInfo);
       
   183 	TInt priv_DoBreakInfo(TGetBreakInfo* aBreakInfo);	
       
   184 	TInt priv_DisableBreakAtAddress(TUint32 aAddress);
       
   185 	TInt priv_DoEnableDisabledBreak(TUint64 aThreadId);
       
   186 	void priv_DoRemoveThreadBreaks(TUint64 aThreadId);
       
   187 	void priv_ClearAllBreakPoints();
       
   188 	TBool priv_IsTemporaryBreak(const TBreakEntry& aBreakEntry) const;
       
   189 
       
   190 	// helper functions
       
   191 	TBool Aligned(TUint32 aAddress, Debug::TArchitectureMode aMode);
       
   192 	TInt BreakSize(Debug::TArchitectureMode aMode);
       
   193 	TBool BreakpointsOverlap(TBreakEntry& aFirst, TBreakEntry& aSecond);
       
   194 	TUint32 BreakInst(Debug::TArchitectureMode aMode);
       
   195 
       
   196 private:
       
   197 	RArray<TBreakEntry> iBreakPointList;
       
   198 	TInt iNextBreakId;
       
   199 
       
   200 	DRM_DebugChannel* iChannel;	// temporary reference back to DRM_DebugChannel to help with refactoring
       
   201 
       
   202 	/* Protect access to the breakpoint list with a DSemaphore
       
   203 	 *
       
   204 	 * This means that stop-mode debuggers know when the list is being updated by the run-mode debug subsystem.
       
   205 	 */
       
   206 	DSemaphore* iLock;
       
   207 
       
   208 	TBool iInitialised;
       
   209 };
       
   210 
       
   211 #include "d_rmd_breakpoints_debug.inl" 
       
   212 
       
   213 #endif