mirror of
https://gitlab.com/freepascal.org/lazarus/lazarus.git
synced 2025-08-18 22:59:07 +02:00
FpDebug: Move getting FrameBase to Context.
This commit is contained in:
parent
515c01c063
commit
2383f18a82
@ -862,7 +862,8 @@ type
|
|||||||
FWatchPointData: TFpWatchPointData;
|
FWatchPointData: TFpWatchPointData;
|
||||||
FProcessConfig: TDbgProcessConfig;
|
FProcessConfig: TDbgProcessConfig;
|
||||||
FConfig: TDbgConfig;
|
FConfig: TDbgConfig;
|
||||||
function DoGetCfiFrameBase(AScope: TFpDbgLocationContext; AnAddr: TDBGPtr): TDBGPtr;
|
function DoGetCfiFrameBase(AContext: TFpDbgLocationContext; out AnError: TFpError): TDBGPtr;
|
||||||
|
function DoGetFrameBase(AContext: TFpDbgLocationContext; out AnError: TFpError): TDBGPtr;
|
||||||
function GetDisassembler: TDbgAsmDecoder;
|
function GetDisassembler: TDbgAsmDecoder;
|
||||||
function GetLastLibrariesLoaded: TDbgLibraryArr;
|
function GetLastLibrariesLoaded: TDbgLibraryArr;
|
||||||
function GetLastLibrariesUnloaded: TDbgLibraryArr;
|
function GetLastLibrariesUnloaded: TDbgLibraryArr;
|
||||||
@ -2622,7 +2623,8 @@ begin
|
|||||||
if Frame <> nil then begin
|
if Frame <> nil then begin
|
||||||
Addr := Frame.AnAddress;
|
Addr := Frame.AnAddress;
|
||||||
Ctx := TFpDbgSimpleLocationContext.Create(MemManager, Addr, DBGPTRSIZE[Mode], AThreadId, AStackFrame);
|
Ctx := TFpDbgSimpleLocationContext.Create(MemManager, Addr, DBGPTRSIZE[Mode], AThreadId, AStackFrame);
|
||||||
Ctx.SetCfiFrameBaseCallback(@DoGetCfiFrameBase);
|
Ctx.SetFrameBaseCallback(@DoGetFrameBase);
|
||||||
|
Ctx.SetCfaFrameBaseCallback(@DoGetCfiFrameBase);
|
||||||
sym := Frame.ProcSymbol;
|
sym := Frame.ProcSymbol;
|
||||||
if sym <> nil then
|
if sym <> nil then
|
||||||
Result := sym.CreateSymbolScope(Ctx);
|
Result := sym.CreateSymbolScope(Ctx);
|
||||||
@ -3097,29 +3099,56 @@ begin
|
|||||||
Result := FDisassembler;
|
Result := FDisassembler;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TDbgProcess.DoGetCfiFrameBase(AScope: TFpDbgLocationContext; AnAddr: TDBGPtr): TDBGPtr;
|
function TDbgProcess.DoGetCfiFrameBase(AContext: TFpDbgLocationContext; out AnError: TFpError
|
||||||
|
): TDBGPtr;
|
||||||
var
|
var
|
||||||
CIE: TDwarfCIE;
|
|
||||||
ROW: TDwarfCallFrameInformationRow;
|
|
||||||
Thrd: TDbgThread;
|
Thrd: TDbgThread;
|
||||||
CStck: TDbgCallstackEntry;
|
CStck: TDbgCallstackEntry;
|
||||||
|
CIE: TDwarfCIE;
|
||||||
|
ROW: TDwarfCallFrameInformationRow;
|
||||||
begin
|
begin
|
||||||
Result := 0;
|
Result := 0;
|
||||||
if (not GetThread(AScope.ThreadId, Thrd)) or (Thrd = nil) then
|
AnError := nil;
|
||||||
|
if (not GetThread(AContext.ThreadId, Thrd)) or (Thrd = nil) then
|
||||||
exit;
|
exit;
|
||||||
if AScope.StackFrame >= Thrd.CallStackEntryList.Count then
|
if AContext.StackFrame >= Thrd.CallStackEntryList.Count then
|
||||||
exit;
|
exit;
|
||||||
CStck := Thrd.CallStackEntryList[AScope.StackFrame];
|
CStck := Thrd.CallStackEntryList[AContext.StackFrame];
|
||||||
if CStck = nil then
|
if CStck = nil then
|
||||||
exit;
|
exit;
|
||||||
|
|
||||||
if not FindCallFrameInfo(AnAddr, CIE, ROW) then
|
if not FindCallFrameInfo(AContext.Address, CIE, ROW) then
|
||||||
exit;
|
exit;
|
||||||
|
|
||||||
if not GetCanonicalFrameAddress(CStck.RegisterValueList ,ROW, Result) then
|
if not GetCanonicalFrameAddress(CStck.RegisterValueList ,ROW, Result) then
|
||||||
Result := 0;
|
Result := 0;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
function TDbgProcess.DoGetFrameBase(AContext: TFpDbgLocationContext; out AnError: TFpError
|
||||||
|
): TDBGPtr;
|
||||||
|
var
|
||||||
|
Thrd: TDbgThread;
|
||||||
|
CStck: TDbgCallstackEntry;
|
||||||
|
p: TFpSymbol;
|
||||||
|
begin
|
||||||
|
Result := 0;
|
||||||
|
AnError := nil;
|
||||||
|
if (not GetThread(AContext.ThreadId, Thrd)) or (Thrd = nil) then
|
||||||
|
exit;
|
||||||
|
if AContext.StackFrame >= Thrd.CallStackEntryList.Count then
|
||||||
|
exit;
|
||||||
|
CStck := Thrd.CallStackEntryList[AContext.StackFrame];
|
||||||
|
if CStck = nil then
|
||||||
|
exit;
|
||||||
|
|
||||||
|
p := CStck.ProcSymbol;
|
||||||
|
if p =nil then
|
||||||
|
exit;
|
||||||
|
|
||||||
|
if p is TFpSymbolDwarfDataProc then
|
||||||
|
Result := TFpSymbolDwarfDataProc(p).GetFrameBase(AContext, AnError);
|
||||||
|
end;
|
||||||
|
|
||||||
function TDbgProcess.GetLastLibrariesLoaded: TDbgLibraryArr;
|
function TDbgProcess.GetLastLibrariesLoaded: TDbgLibraryArr;
|
||||||
begin
|
begin
|
||||||
Result := FLibMap.FLibrariesAdded;
|
Result := FLibMap.FLibrariesAdded;
|
||||||
|
@ -558,14 +558,10 @@ type
|
|||||||
TFpSymbolDwarf = class(TDbgDwarfSymbolBase)
|
TFpSymbolDwarf = class(TDbgDwarfSymbolBase)
|
||||||
private
|
private
|
||||||
FNestedTypeInfo: TFpSymbolDwarfType;
|
FNestedTypeInfo: TFpSymbolDwarfType;
|
||||||
(* FLocalProcInfo: the procedure in which a local symbol is defined/used *)
|
|
||||||
FLocalProcInfo: TFpSymbolDwarf;
|
|
||||||
FDwarfReadFlags: set of (didtNameRead, didtTypeRead, didtArtificialRead, didtIsArtifical);
|
FDwarfReadFlags: set of (didtNameRead, didtTypeRead, didtArtificialRead, didtIsArtifical);
|
||||||
function GetNestedTypeInfo: TFpSymbolDwarfType;
|
function GetNestedTypeInfo: TFpSymbolDwarfType;
|
||||||
function GetTypeInfo: TFpSymbolDwarfType; inline;
|
function GetTypeInfo: TFpSymbolDwarfType; inline;
|
||||||
protected
|
protected
|
||||||
procedure SetLocalProcInfo(AValue: TFpSymbolDwarf); virtual;
|
|
||||||
|
|
||||||
function DoGetNestedTypeInfo: TFpSymbolDwarfType; virtual;
|
function DoGetNestedTypeInfo: TFpSymbolDwarfType; virtual;
|
||||||
function ReadMemberVisibility(out AMemberVisibility: TDbgSymbolMemberVisibility): Boolean;
|
function ReadMemberVisibility(out AMemberVisibility: TDbgSymbolMemberVisibility): Boolean;
|
||||||
function IsArtificial: Boolean; // usud by formal param and subprogram
|
function IsArtificial: Boolean; // usud by formal param and subprogram
|
||||||
@ -573,9 +569,6 @@ type
|
|||||||
procedure TypeInfoNeeded; override;
|
procedure TypeInfoNeeded; override;
|
||||||
property NestedTypeInfo: TFpSymbolDwarfType read GetNestedTypeInfo;
|
property NestedTypeInfo: TFpSymbolDwarfType read GetNestedTypeInfo;
|
||||||
|
|
||||||
// LocalProcInfo: funtion for local var / param
|
|
||||||
property LocalProcInfo: TFpSymbolDwarf read FLocalProcInfo write SetLocalProcInfo;
|
|
||||||
|
|
||||||
function DoForwardReadSize(const AValueObj: TFpValue; out ASize: TFpDbgValueSize): Boolean; inline;
|
function DoForwardReadSize(const AValueObj: TFpValue; out ASize: TFpDbgValueSize): Boolean; inline;
|
||||||
function DoReadDataSize(const AValueObj: TFpValue; out ADataSize: TFpDbgValueSize): Boolean; virtual;
|
function DoReadDataSize(const AValueObj: TFpValue; out ADataSize: TFpDbgValueSize): Boolean; virtual;
|
||||||
protected
|
protected
|
||||||
@ -650,12 +643,8 @@ type
|
|||||||
{ TFpSymbolDwarfDataWithLocation }
|
{ TFpSymbolDwarfDataWithLocation }
|
||||||
|
|
||||||
TFpSymbolDwarfDataWithLocation = class(TFpSymbolDwarfData)
|
TFpSymbolDwarfDataWithLocation = class(TFpSymbolDwarfData)
|
||||||
private
|
|
||||||
procedure FrameBaseNeeded(ASender: TObject); // Sender = TDwarfLocationExpression
|
|
||||||
protected
|
protected
|
||||||
function GetValueObject: TFpValue; override;
|
function GetValueObject: TFpValue; override;
|
||||||
function InitLocationParser(const ALocationParser: TDwarfLocationExpression;
|
|
||||||
AnInitLocParserData: PInitLocParserData): Boolean; override;
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
TFpSymbolDwarfThirdPartyExtension = class(TFpSymbolDwarf)
|
TFpSymbolDwarfThirdPartyExtension = class(TFpSymbolDwarf)
|
||||||
@ -1091,7 +1080,6 @@ DECL = DW_AT_decl_column, DW_AT_decl_file, DW_AT_decl_line
|
|||||||
procedure DoReferenceReleased; override;
|
procedure DoReferenceReleased; override;
|
||||||
function GetLineEndAddress: TDBGPtr; override;
|
function GetLineEndAddress: TDBGPtr; override;
|
||||||
function GetLineStartAddress: TDBGPtr; override;
|
function GetLineStartAddress: TDBGPtr; override;
|
||||||
function GetFrameBase(ASender: TDwarfLocationExpression): TDbgPtr;
|
|
||||||
function GetFlags: TDbgSymbolFlags; override;
|
function GetFlags: TDbgSymbolFlags; override;
|
||||||
procedure TypeInfoNeeded; override;
|
procedure TypeInfoNeeded; override;
|
||||||
|
|
||||||
@ -1115,6 +1103,7 @@ DECL = DW_AT_decl_column, DW_AT_decl_file, DW_AT_decl_line
|
|||||||
function CreateSymbolScope(ALocationContext: TFpDbgLocationContext; ADwarfInfo: TFpDwarfInfo): TFpDbgSymbolScope; override;
|
function CreateSymbolScope(ALocationContext: TFpDbgLocationContext; ADwarfInfo: TFpDwarfInfo): TFpDbgSymbolScope; override;
|
||||||
// TODO members = locals ?
|
// TODO members = locals ?
|
||||||
function GetSelfParameter(AnAddress: TDbgPtr = 0): TFpValueDwarf;
|
function GetSelfParameter(AnAddress: TDbgPtr = 0): TFpValueDwarf;
|
||||||
|
function GetFrameBase(AContext: TFpDbgLocationContext; out AnError: TFpError): TDbgPtr;
|
||||||
|
|
||||||
function ResolveInternalFinallySymbol(Process: Pointer): TFpSymbol; virtual; // so it can be overriden by the fpc classes
|
function ResolveInternalFinallySymbol(Process: Pointer): TFpSymbol; virtual; // so it can be overriden by the fpc classes
|
||||||
|
|
||||||
@ -1719,8 +1708,6 @@ begin
|
|||||||
exit;
|
exit;
|
||||||
if InfoEntry.IsAddressInStartScope(FAddress) and not InfoEntry.IsArtificial then begin
|
if InfoEntry.IsAddressInStartScope(FAddress) and not InfoEntry.IsArtificial then begin
|
||||||
ADbgValue := SymbolToValue(TFpSymbolDwarf.CreateSubClass(AName, InfoEntry));
|
ADbgValue := SymbolToValue(TFpSymbolDwarf.CreateSubClass(AName, InfoEntry));
|
||||||
if ADbgValue <> nil then
|
|
||||||
TFpSymbolDwarf(ADbgValue.DbgSymbol).LocalProcInfo := TFpSymbolDwarfDataProc(FSymbol);
|
|
||||||
end;
|
end;
|
||||||
Result := ADbgValue <> nil;
|
Result := ADbgValue <> nil;
|
||||||
end;
|
end;
|
||||||
@ -4265,18 +4252,6 @@ begin
|
|||||||
Result := TFpSymbolDwarfType(inherited TypeInfo);
|
Result := TFpSymbolDwarfType(inherited TypeInfo);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TFpSymbolDwarf.SetLocalProcInfo(AValue: TFpSymbolDwarf);
|
|
||||||
begin
|
|
||||||
if FLocalProcInfo = AValue then exit;
|
|
||||||
|
|
||||||
FLocalProcInfo.ReleaseReference{$IFDEF WITH_REFCOUNT_DEBUG}(@FLocalProcInfo, 'FLocalProcInfo'){$ENDIF};
|
|
||||||
|
|
||||||
FLocalProcInfo := AValue;
|
|
||||||
|
|
||||||
if (FLocalProcInfo <> nil) then
|
|
||||||
FLocalProcInfo.AddReference{$IFDEF WITH_REFCOUNT_DEBUG}(@FLocalProcInfo, 'FLocalProcInfo'){$ENDIF};
|
|
||||||
end;
|
|
||||||
|
|
||||||
function TFpSymbolDwarf.DoGetNestedTypeInfo: TFpSymbolDwarfType;
|
function TFpSymbolDwarf.DoGetNestedTypeInfo: TFpSymbolDwarfType;
|
||||||
var
|
var
|
||||||
FwdInfoPtr: Pointer;
|
FwdInfoPtr: Pointer;
|
||||||
@ -4945,7 +4920,6 @@ destructor TFpSymbolDwarf.Destroy;
|
|||||||
begin
|
begin
|
||||||
inherited Destroy;
|
inherited Destroy;
|
||||||
FNestedTypeInfo.ReleaseReference{$IFDEF WITH_REFCOUNT_DEBUG}(@FNestedTypeInfo, ClassName+'.FNestedTypeInfo'){$ENDIF};
|
FNestedTypeInfo.ReleaseReference{$IFDEF WITH_REFCOUNT_DEBUG}(@FNestedTypeInfo, ClassName+'.FNestedTypeInfo'){$ENDIF};
|
||||||
FLocalProcInfo.ReleaseReference{$IFDEF WITH_REFCOUNT_DEBUG}(@FLocalProcInfo, 'FLocalProcInfo'){$ENDIF};
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TFpSymbolDwarf.StartScope: TDbgPtr;
|
function TFpSymbolDwarf.StartScope: TDbgPtr;
|
||||||
@ -5046,39 +5020,6 @@ end;
|
|||||||
|
|
||||||
{ TFpSymbolDwarfDataWithLocation }
|
{ TFpSymbolDwarfDataWithLocation }
|
||||||
|
|
||||||
function TFpSymbolDwarfDataWithLocation.InitLocationParser(const ALocationParser: TDwarfLocationExpression;
|
|
||||||
AnInitLocParserData: PInitLocParserData): Boolean;
|
|
||||||
begin
|
|
||||||
Result := inherited InitLocationParser(ALocationParser, AnInitLocParserData);
|
|
||||||
ALocationParser.OnFrameBaseNeeded := @FrameBaseNeeded;
|
|
||||||
end;
|
|
||||||
|
|
||||||
procedure TFpSymbolDwarfDataWithLocation.FrameBaseNeeded(ASender: TObject);
|
|
||||||
var
|
|
||||||
p: TFpSymbolDwarf;
|
|
||||||
fb: TDBGPtr;
|
|
||||||
begin
|
|
||||||
debugln(FPDBG_DWARF_SEARCH, ['TFpSymbolDwarfDataVariable.FrameBaseNeeded ']);
|
|
||||||
p := LocalProcInfo;
|
|
||||||
// TODO: what if parent is declaration?
|
|
||||||
if p is TFpSymbolDwarfDataProc then begin
|
|
||||||
fb := TFpSymbolDwarfDataProc(p).GetFrameBase(ASender as TDwarfLocationExpression);
|
|
||||||
(ASender as TDwarfLocationExpression).FrameBase := fb;
|
|
||||||
if fb = 0 then begin
|
|
||||||
debugln(FPDBG_DWARF_ERRORS, ['DWARF ERROR in TFpSymbolDwarfDataWithLocation.FrameBaseNeeded result is 0']);
|
|
||||||
end;
|
|
||||||
exit;
|
|
||||||
end;
|
|
||||||
|
|
||||||
{$warning TODO}
|
|
||||||
//else
|
|
||||||
//if ParentTypeInfo <> nil then
|
|
||||||
// ParentTypeInfo.fr;
|
|
||||||
// TODO: check owner
|
|
||||||
debugln(FPDBG_DWARF_ERRORS, ['DWARF ERROR in TFpSymbolDwarfDataWithLocation.FrameBaseNeeded no parent type info']);
|
|
||||||
(ASender as TDwarfLocationExpression).FrameBase := 0;
|
|
||||||
end;
|
|
||||||
|
|
||||||
function TFpSymbolDwarfDataWithLocation.GetValueObject: TFpValue;
|
function TFpSymbolDwarfDataWithLocation.GetValueObject: TFpValue;
|
||||||
var
|
var
|
||||||
ti: TFpSymbol;
|
ti: TFpSymbol;
|
||||||
@ -7005,12 +6946,14 @@ begin
|
|||||||
NilThenReleaseRef(TFpSymbolDwarfTypeProc(TypeInfo).FLastMember {$IFDEF WITH_REFCOUNT_DEBUG}, 'TFpSymbolDwarfDataProc.FLastMember'{$ENDIF});
|
NilThenReleaseRef(TFpSymbolDwarfTypeProc(TypeInfo).FLastMember {$IFDEF WITH_REFCOUNT_DEBUG}, 'TFpSymbolDwarfDataProc.FLastMember'{$ENDIF});
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TFpSymbolDwarfDataProc.GetFrameBase(ASender: TDwarfLocationExpression): TDbgPtr;
|
function TFpSymbolDwarfDataProc.GetFrameBase(AContext: TFpDbgLocationContext; out AnError: TFpError
|
||||||
|
): TDbgPtr;
|
||||||
var
|
var
|
||||||
Val: TByteDynArray;
|
Val: TByteDynArray;
|
||||||
rd: TFpDbgMemLocation;
|
rd: TFpDbgMemLocation;
|
||||||
begin
|
begin
|
||||||
Result := 0;
|
Result := 0;
|
||||||
|
AnError := nil;
|
||||||
if FFrameBaseParser = nil then begin
|
if FFrameBaseParser = nil then begin
|
||||||
//TODO: avoid copying data
|
//TODO: avoid copying data
|
||||||
if not InformationEntry.ReadValue(DW_AT_frame_base, Val) then begin
|
if not InformationEntry.ReadValue(DW_AT_frame_base, Val) then begin
|
||||||
@ -7024,15 +6967,14 @@ begin
|
|||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
FFrameBaseParser := TDwarfLocationExpression.Create(@Val[0], Length(Val), CompilationUnit,
|
FFrameBaseParser := TDwarfLocationExpression.Create(@Val[0], Length(Val), CompilationUnit, AContext);
|
||||||
ASender.Context);
|
|
||||||
FFrameBaseParser.IsDwAtFrameBase := True;
|
FFrameBaseParser.IsDwAtFrameBase := True;
|
||||||
FFrameBaseParser.Evaluate;
|
FFrameBaseParser.Evaluate;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
if IsError(FFrameBaseParser.LastError) then begin
|
if IsError(FFrameBaseParser.LastError) then begin
|
||||||
ASender.SetLastError(FFrameBaseParser.LastError);
|
AnError := FFrameBaseParser.LastError;
|
||||||
debugln(FPDBG_DWARF_ERRORS, ['TFpSymbolDwarfDataProc.GetFrameBase location parser failed ', ErrorHandler.ErrorAsString(ASender.LastError)]);
|
debugln(FPDBG_DWARF_ERRORS, ['TFpSymbolDwarfDataProc.GetFrameBase location parser failed ', ErrorHandler.ErrorAsString(AnError)]);
|
||||||
end
|
end
|
||||||
else begin
|
else begin
|
||||||
rd := FFrameBaseParser.ResultData;
|
rd := FFrameBaseParser.ResultData;
|
||||||
@ -7129,7 +7071,6 @@ begin
|
|||||||
Result := TFpValueDwarf(TFpSymbolDwarfData.CreateValueSubClass('self', InfoEntry).Value);
|
Result := TFpValueDwarf(TFpSymbolDwarfData.CreateValueSubClass('self', InfoEntry).Value);
|
||||||
if Result <> nil then begin
|
if Result <> nil then begin
|
||||||
Result.FDataSymbol.ReleaseReference;
|
Result.FDataSymbol.ReleaseReference;
|
||||||
Result.FDataSymbol.LocalProcInfo := Self;
|
|
||||||
end;
|
end;
|
||||||
debugln(FPDBG_DWARF_SEARCH, ['TFpSymbolDwarfDataProc.GetSelfParameter ', InfoEntry.ScopeDebugText, DbgSName(Result)]);
|
debugln(FPDBG_DWARF_SEARCH, ['TFpSymbolDwarfDataProc.GetSelfParameter ', InfoEntry.ScopeDebugText, DbgSName(Result)]);
|
||||||
end;
|
end;
|
||||||
@ -7207,8 +7148,6 @@ begin
|
|||||||
FLastMember := TFpSymbolDwarf.CreateSubClass('', TDwarfInformationEntry(FProcMembers[AIndex]));
|
FLastMember := TFpSymbolDwarf.CreateSubClass('', TDwarfInformationEntry(FProcMembers[AIndex]));
|
||||||
{$IFDEF WITH_REFCOUNT_DEBUG}FLastMember.DbgRenameReference(@FLastMember, 'TFpSymbolDwarfDataProc.FLastMember');{$ENDIF}
|
{$IFDEF WITH_REFCOUNT_DEBUG}FLastMember.DbgRenameReference(@FLastMember, 'TFpSymbolDwarfDataProc.FLastMember');{$ENDIF}
|
||||||
Result := FLastMember;
|
Result := FLastMember;
|
||||||
//if Result <> nil then
|
|
||||||
// TFpSymbolDwarf(Result).LocalProcInfo := FProcValue;
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TFpSymbolDwarfTypeProc.GetNestedSymbolExByName(const AIndex: String;
|
function TFpSymbolDwarfTypeProc.GetNestedSymbolExByName(const AIndex: String;
|
||||||
@ -7231,8 +7170,6 @@ begin
|
|||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
Result := FLastMember;
|
Result := FLastMember;
|
||||||
//if Result <> nil then
|
|
||||||
// TFpSymbolDwarf(Result).LocalProcInfo := FProcValue;
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TFpSymbolDwarfTypeProc.GetNestedSymbolCount: Integer;
|
function TFpSymbolDwarfTypeProc.GetNestedSymbolCount: Integer;
|
||||||
|
@ -872,7 +872,6 @@ type
|
|||||||
FFrameBase: TDbgPtr;
|
FFrameBase: TDbgPtr;
|
||||||
FIsDwAtFrameBase: Boolean;
|
FIsDwAtFrameBase: Boolean;
|
||||||
FLastError: TFpError;
|
FLastError: TFpError;
|
||||||
FOnFrameBaseNeeded: TNotifyEvent;
|
|
||||||
FStack: TDwarfLocationStack;
|
FStack: TDwarfLocationStack;
|
||||||
FCU: TDwarfCompilationUnit;
|
FCU: TDwarfCompilationUnit;
|
||||||
FData: PByte;
|
FData: PByte;
|
||||||
@ -885,8 +884,7 @@ type
|
|||||||
procedure Evaluate;
|
procedure Evaluate;
|
||||||
function ResultData: TFpDbgMemLocation;
|
function ResultData: TFpDbgMemLocation;
|
||||||
procedure Push(const AValue: TFpDbgMemLocation);
|
procedure Push(const AValue: TFpDbgMemLocation);
|
||||||
property FrameBase: TDbgPtr read FFrameBase write FFrameBase;
|
//property FrameBase: TDbgPtr read FFrameBase write FFrameBase;
|
||||||
property OnFrameBaseNeeded: TNotifyEvent read FOnFrameBaseNeeded write FOnFrameBaseNeeded;
|
|
||||||
property LastError: TFpError read FLastError;
|
property LastError: TFpError read FLastError;
|
||||||
property Context: TFpDbgLocationContext read FContext write FContext;
|
property Context: TFpDbgLocationContext read FContext write FContext;
|
||||||
// for DW_OP_push_object_address
|
// for DW_OP_push_object_address
|
||||||
@ -2170,6 +2168,17 @@ var
|
|||||||
CurInstr, CurData: PByte;
|
CurInstr, CurData: PByte;
|
||||||
AddrSize: Byte;
|
AddrSize: Byte;
|
||||||
|
|
||||||
|
procedure SetError(AnError: TFpError);
|
||||||
|
begin
|
||||||
|
FStack.Push(InvalidLoc); // Mark as failed
|
||||||
|
FLastError := AnError;
|
||||||
|
debugln(FPDBG_DWARF_ERRORS,
|
||||||
|
['DWARF ERROR in TDwarfLocationExpression: Failed at Pos=', CurInstr-FData,
|
||||||
|
' OpCode=', IntToHex(CurInstr^, 2), ' Depth=', FStack.Count,
|
||||||
|
' Data: ', dbgMemRange(FData, FMaxData-FData),
|
||||||
|
' Extra: ', ErrorHandler.ErrorAsString(AnError) ]);
|
||||||
|
end;
|
||||||
|
|
||||||
procedure SetError(AnInternalErrorCode: TFpErrorCode = fpErrNoError);
|
procedure SetError(AnInternalErrorCode: TFpErrorCode = fpErrNoError);
|
||||||
begin
|
begin
|
||||||
FStack.Push(InvalidLoc); // Mark as failed
|
FStack.Push(InvalidLoc); // Mark as failed
|
||||||
@ -2345,12 +2354,13 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
DW_OP_fbreg: begin
|
DW_OP_fbreg: begin
|
||||||
if (FFrameBase = 0) and (FOnFrameBaseNeeded <> nil) then FOnFrameBaseNeeded(Self);
|
if (FFrameBase = 0) then begin
|
||||||
if FFrameBase = 0 then begin
|
FFrameBase := FContext.FrameBase;
|
||||||
if not IsError(FLastError) then
|
if FFrameBase = 0 then
|
||||||
SetError;
|
SetError(FContext.FrameBaseError);
|
||||||
exit;
|
|
||||||
end;
|
end;
|
||||||
|
if FFrameBase = 0 then
|
||||||
|
exit;
|
||||||
{$PUSH}{$R-}{$Q-}
|
{$PUSH}{$R-}{$Q-}
|
||||||
FStack.PushTargetMem(FFrameBase+SLEB128toOrdinal(CurData));
|
FStack.PushTargetMem(FFrameBase+SLEB128toOrdinal(CurData));
|
||||||
{$POP}
|
{$POP}
|
||||||
@ -2626,9 +2636,9 @@ begin
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
DW_OP_call_frame_cfa: begin
|
DW_OP_call_frame_cfa: begin
|
||||||
NewValue := Context.CfiFrameBase;
|
NewValue := Context.CfaFrameBase;
|
||||||
if NewValue = 0 then begin
|
if NewValue = 0 then begin
|
||||||
SetError(fpErrLocationParser);
|
SetError(Context.FCfarameBaseError);
|
||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
FStack.PushTargetMem(NewValue);
|
FStack.PushTargetMem(NewValue);
|
||||||
|
@ -82,14 +82,18 @@ type
|
|||||||
|
|
||||||
TFpDbgLocationContext = class;
|
TFpDbgLocationContext = class;
|
||||||
|
|
||||||
TGetCfiFrameBaseCallback = function(AScope: TFpDbgLocationContext; AnAddr: TDBGPtr): TDBGPtr of object;
|
TGetFrameBaseCallback = function(AContext: TFpDbgLocationContext; out AnError: TFpError): TDBGPtr of object;
|
||||||
|
|
||||||
TFpDbgLocationContext = class(TRefCountedObject)
|
TFpDbgLocationContext = class(TRefCountedObject)
|
||||||
private
|
private
|
||||||
FCfiFrameBaseCallback: TGetCfiFrameBaseCallback;
|
FCfaFrameBaseError: TFpError;
|
||||||
FCfiFrameBase: TDBGPtr;
|
FFrameBaseCallback: TGetFrameBaseCallback;
|
||||||
|
FCfaFrameBaseCallback: TGetFrameBaseCallback;
|
||||||
|
FFrameBaseError: TFpError;
|
||||||
|
FFrameBase, FCfaFrameBase: TDBGPtr;
|
||||||
|
|
||||||
function GetCfiFrameBase: TDBGPtr;
|
function GetFrameBase: TDBGPtr;
|
||||||
|
function GetCfaFrameBase: TDBGPtr;
|
||||||
function GetLastMemError: TFpError;
|
function GetLastMemError: TFpError;
|
||||||
function GetPartialReadResultLenght: QWord;
|
function GetPartialReadResultLenght: QWord;
|
||||||
protected
|
protected
|
||||||
@ -101,14 +105,19 @@ type
|
|||||||
function GetMemModel: TFpDbgMemModel; virtual; abstract;
|
function GetMemModel: TFpDbgMemModel; virtual; abstract;
|
||||||
public
|
public
|
||||||
property Address: TDbgPtr read GetAddress;
|
property Address: TDbgPtr read GetAddress;
|
||||||
property CfiFrameBase: TDBGPtr read GetCfiFrameBase;
|
|
||||||
property ThreadId: Integer read GetThreadId;
|
property ThreadId: Integer read GetThreadId;
|
||||||
property StackFrame: Integer read GetStackFrame;
|
property StackFrame: Integer read GetStackFrame;
|
||||||
property SizeOfAddress: Integer read GetSizeOfAddress;
|
property SizeOfAddress: Integer read GetSizeOfAddress;
|
||||||
property MemManager: TFpDbgMemManager read GetMemManager;
|
property MemManager: TFpDbgMemManager read GetMemManager;
|
||||||
property MemModel: TFpDbgMemModel read GetMemModel;
|
property MemModel: TFpDbgMemModel read GetMemModel;
|
||||||
public
|
public
|
||||||
procedure SetCfiFrameBaseCallback(ACallback: TGetCfiFrameBaseCallback);
|
procedure SetFrameBaseCallback(ACallback: TGetFrameBaseCallback);
|
||||||
|
procedure SetCfaFrameBaseCallback(ACallback: TGetFrameBaseCallback);
|
||||||
|
property FrameBase: TDBGPtr read GetFrameBase; // as requested by DW_OP_fbreg
|
||||||
|
property FrameBaseError: TFpError read FFrameBaseError;
|
||||||
|
property CfaFrameBase: TDBGPtr read GetCfaFrameBase; // as requested by DW_OP_call_frame_cfa
|
||||||
|
property FCfarameBaseError: TFpError read FCfaFrameBaseError;
|
||||||
|
public
|
||||||
procedure ClearLastMemError;
|
procedure ClearLastMemError;
|
||||||
property LastMemError: TFpError read GetLastMemError;
|
property LastMemError: TFpError read GetLastMemError;
|
||||||
property PartialReadResultLenght: QWord read GetPartialReadResultLenght;
|
property PartialReadResultLenght: QWord read GetPartialReadResultLenght;
|
||||||
@ -987,12 +996,26 @@ begin
|
|||||||
Result := MemManager.LastError;
|
Result := MemManager.LastError;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TFpDbgLocationContext.GetCfiFrameBase: TDBGPtr;
|
function TFpDbgLocationContext.GetFrameBase: TDBGPtr;
|
||||||
begin
|
begin
|
||||||
if FCfiFrameBaseCallback <> nil then
|
if FFrameBaseCallback <> nil then begin
|
||||||
FCfiFrameBase := FCfiFrameBaseCallback(Self, Address);
|
FFrameBase := FFrameBaseCallback(Self, FFrameBaseError);
|
||||||
FCfiFrameBaseCallback := nil; // Only call once
|
if (FFrameBase = 0) and not IsError(FFrameBaseError) then
|
||||||
Result := FCfiFrameBase;
|
FFrameBaseError := CreateError(fpErrAnyError, []);
|
||||||
|
FFrameBaseCallback := nil;
|
||||||
|
end;
|
||||||
|
Result := FFrameBase;
|
||||||
|
end;
|
||||||
|
|
||||||
|
function TFpDbgLocationContext.GetCfaFrameBase: TDBGPtr;
|
||||||
|
begin
|
||||||
|
if FCfaFrameBaseCallback <> nil then begin
|
||||||
|
FCfaFrameBase := FCfaFrameBaseCallback(Self, FCfaFrameBaseError);
|
||||||
|
if (FCfaFrameBase = 0) and not IsError(FCfaFrameBaseError) then
|
||||||
|
FCfaFrameBaseError := CreateError(fpErrAnyError, []);
|
||||||
|
FCfaFrameBaseCallback := nil;
|
||||||
|
end;
|
||||||
|
Result := FCfaFrameBase;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TFpDbgLocationContext.GetPartialReadResultLenght: QWord;
|
function TFpDbgLocationContext.GetPartialReadResultLenght: QWord;
|
||||||
@ -1000,9 +1023,14 @@ begin
|
|||||||
Result := MemManager.PartialReadResultLenght;
|
Result := MemManager.PartialReadResultLenght;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TFpDbgLocationContext.SetCfiFrameBaseCallback(ACallback: TGetCfiFrameBaseCallback);
|
procedure TFpDbgLocationContext.SetFrameBaseCallback(ACallback: TGetFrameBaseCallback);
|
||||||
begin
|
begin
|
||||||
FCfiFrameBaseCallback := ACallback;
|
FFrameBaseCallback := ACallback;
|
||||||
|
end;
|
||||||
|
|
||||||
|
procedure TFpDbgLocationContext.SetCfaFrameBaseCallback(ACallback: TGetFrameBaseCallback);
|
||||||
|
begin
|
||||||
|
FCfaFrameBaseCallback := ACallback;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TFpDbgLocationContext.ClearLastMemError;
|
procedure TFpDbgLocationContext.ClearLastMemError;
|
||||||
|
Loading…
Reference in New Issue
Block a user