MG: splitted main.pp: debugger management in TDebugManager

git-svn-id: trunk@1552 -
This commit is contained in:
lazarus 2002-03-27 10:39:44 +00:00
parent 1ac990f79a
commit 1e999a3d60
7 changed files with 675 additions and 532 deletions

2
.gitattributes vendored
View File

@ -117,6 +117,7 @@ examples/testallform.pp svneol=native#text/pascal
examples/testtools.inc svneol=native#text/pascal
examples/toolbar.pp svneol=native#text/pascal
examples/trackbar.pp svneol=native#text/pascal
ide/basedebugmanager.pas svneol=native#text/pascal
ide/buildlazdialog.pas svneol=native#text/pascal
ide/codetemplatedialog.pp svneol=native#text/pascal
ide/codetoolsdefines.lrs svneol=native#text/pascal
@ -127,6 +128,7 @@ ide/compiler.pp svneol=native#text/pascal
ide/compileroptions.pp svneol=native#text/pascal
ide/compreg.pp svneol=native#text/pascal
ide/customformeditor.pp svneol=native#text/pascal
ide/debugmanager.pas svneol=native#text/pascal
ide/editdefinetree.pas svneol=native#text/pascal
ide/editoroptions.lrs svneol=native#text/pascal
ide/editoroptions.pp svneol=native#text/pascal

View File

@ -1078,13 +1078,11 @@ writeln('TCodeCompletionCodeTool.CreateMissingProcBodies Gather existing method
AnAVLNode:=ClassProcs.FindLowest;
while AnAVLNode<>nil do begin
NextAVLNode:=ClassProcs.FindSuccessor(AnAVLNode);
if NextAVLNode<>nil then begin
ANodeExt:=TCodeTreeNodeExtension(AnAVLNode.Data);
ANode:=ANodeExt.Node;
if (ANode<>nil) and (ANode.Desc=ctnProcedure)
and ProcNodeHasSpecifier(ANode,psABSTRACT) then begin
ClassProcs.Delete(AnAVLNode);
end;
ANodeExt:=TCodeTreeNodeExtension(AnAVLNode.Data);
ANode:=ANodeExt.Node;
if (ANode<>nil) and (ANode.Desc=ctnProcedure)
and ProcNodeHasSpecifier(ANode,psABSTRACT) then begin
ClassProcs.Delete(AnAVLNode);
end;
AnAVLNode:=NextAVLNode;
end;

58
ide/basedebugmanager.pas Normal file
View File

@ -0,0 +1,58 @@
{ $Id$ }
{
/***************************************************************************
basedebugmanager.pp
-------------------
TBaseDebugManager is the base class for TDebugManager, which controls all
debugging related stuff in the IDE. The base class is mostly abstract.
***************************************************************************/
/***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/
}
unit BaseDebugManager;
{$mode objfpc}{$H+}
interface
{$I ide.inc}
uses
{$IFDEF IDE_MEM_CHECK}
MemCheck,
{$ENDIF}
Classes, SysUtils, Forms;
type
TBaseDebugManager = class(TComponent)
public
procedure ConnectMainBarEvents; virtual; abstract;
procedure ConnectSourceNotebookEvents; virtual; abstract;
procedure SetupMainBarShortCuts; virtual; abstract;
function DoInitDebugger: TModalResult; virtual; abstract;
function DoPauseProject: TModalResult; virtual; abstract;
function DoStepIntoProject: TModalResult; virtual; abstract;
function DoStepOverProject: TModalResult; virtual; abstract;
function DoRunToCursor: TModalResult; virtual; abstract;
function DoStopProject: TModalResult; virtual; abstract;
procedure RunDebugger; virtual; abstract;
procedure EndDebugging; virtual; abstract;
end;
var DebugBoss: TBaseDebugManager;
implementation
end.

524
ide/debugmanager.pas Normal file
View File

@ -0,0 +1,524 @@
{ $Id$ }
{
/***************************************************************************
debugmanager.pp
---------------
TDebugManager controls all debugging related stuff in the IDE.
***************************************************************************/
/***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/
}
unit DebugManager;
{$mode objfpc}{$H+}
interface
{$I ide.inc}
uses
{$IFDEF IDE_MEM_CHECK}
MemCheck,
{$ENDIF}
Classes, SysUtils, Forms, Controls, Dialogs, CompilerOptions, EditorOptions,
EnvironmentOpts, KeyMapping, UnitEditor, Project, IDEProcs,
Debugger, DBGOutputForm, GDBMIDebugger, RunParamsOpts, ExtToolDialog,
ProjectDefs, Watchesdlg, BreakPointsdlg, LocalsDlg, DebuggerDlg,
BaseDebugManager, MainBar;
type
TDebugManager = class(TBaseDebugManager)
// Menu events
procedure mnuViewWatchesClick(Sender: TObject);
procedure mnuViewBreakPointsClick(Sender: TObject);
procedure mnuViewDebugOutputClick(Sender: TObject);
procedure mnuViewLocalsClick(Sender: TObject);
// SrcNotebook events
procedure OnSrcNotebookAddWatchesAtCursor(Sender: TObject);
procedure OnSrcNotebookCreateBreakPoint(Sender: TObject; Line: Integer);
procedure OnSrcNotebookDeleteBreakPoint(Sender: TObject; Line: Integer);
// Debugger events
procedure OnDebuggerChangeState(Sender: TObject);
procedure OnDebuggerCurrentLine(Sender: TObject; const ALocation: TDBGLocationRec);
procedure OnDebuggerOutput(Sender: TObject; const AText: String);
procedure OnDebuggerException(Sender: TObject; const AExceptionID: Integer; const AExceptionText: String);
private
FBreakPoints: TDBGBreakPoints; // Points to debugger breakpoints if available
// Else to own objet
FDebugOutputDlg: TDBGOutputForm;
FBreakPointsDlg: TBreakPointsDlg;
FLocalsDlg: TLocalsDlg;
FDebugger: TDebugger;
procedure DebugConstructor;
procedure DebugDialogDestroy(Sender: TObject);
procedure ViewDebugDialog(const ADialogClass: TDebuggerDlgClass; var ADialog: TDebuggerDlg);
public
constructor Create(TheOwner: TComponent); override;
destructor Destroy; override;
procedure ConnectMainBarEvents; override;
procedure ConnectSourceNotebookEvents; override;
procedure SetupMainBarShortCuts; override;
function DoInitDebugger: TModalResult; override;
function DoPauseProject: TModalResult; override;
function DoStepIntoProject: TModalResult; override;
function DoStepOverProject: TModalResult; override;
function DoRunToCursor: TModalResult; override;
function DoStopProject: TModalResult; override;
procedure RunDebugger; override;
procedure EndDebugging; override;
end;
implementation
procedure TDebugManager.DebugConstructor;
begin
// TWatchesDlg
Watches_Dlg := TWatchesDlg.Create(Self);
FBreakPointsDlg := nil;
FLocalsDlg := nil;
FDebugger := nil;
FBreakPoints := TDBGBreakPoints.Create(nil, TDBGBreakPoint);
end;
//-----------------------------------------------------------------------------
// Menu events
//-----------------------------------------------------------------------------
procedure TDebugManager.mnuViewWatchesClick(Sender : TObject);
begin
Watches_dlg.Show;
end;
procedure TDebugManager.mnuViewBreakPointsClick(Sender : TObject);
begin
ViewDebugDialog(TBreakPointsDlg, FBreakPointsDlg);
end;
procedure TDebugManager.mnuViewDebugOutputClick(Sender : TObject);
begin
ViewDebugDialog(TDBGOutputForm, FDebugOutputDlg);
end;
procedure TDebugManager.mnuViewLocalsClick(Sender : TObject);
begin
ViewDebugDialog(TLocalsDlg, FLocalsDlg);
end;
//-----------------------------------------------------------------------------
// ScrNoteBook events
//-----------------------------------------------------------------------------
procedure TDebugManager.OnSrcNotebookAddWatchesAtCursor(Sender : TObject);
var
SE : TSourceEditor;
WatchVar: String;
NewWatch: TdbgWatch;
begin
if FDebugger = nil then Exit;
//get the sourceEditor.
SE := TSourceNotebook(sender).GetActiveSE;
if not Assigned(SE) then Exit;
WatchVar := SE.GetWordAtCurrentCaret;
if WatchVar = '' then Exit;
NewWatch := TdbgWatch(FDebugger.Watches.Add);
NewWatch.Expression := WatchVar;
NewWatch.Enabled := True;
end;
procedure TDebugManager.OnSrcNotebookCreateBreakPoint(Sender: TObject; Line: Integer);
var
NewBreak: TDBGBreakPoint;
begin
if SourceNotebook.Notebook = nil then Exit;
NewBreak := FBreakPoints.Add(ExtractFilename(TSourceNotebook(sender).GetActiveSe.FileName), Line);
NewBreak.Enabled := True;
end;
procedure TDebugManager.OnSrcNotebookDeleteBreakPoint(Sender: TObject; Line: Integer);
begin
if SourceNotebook.Notebook = nil then Exit;
FBreakPoints.Find(ExtractFilename(TSourceNotebook(sender).GetActiveSe.FileName), Line).Free;
end;
//-----------------------------------------------------------------------------
// Debugger events
//-----------------------------------------------------------------------------
procedure TDebugManager.OnDebuggerException(Sender: TObject; const AExceptionID: Integer; const AExceptionText: String);
begin
MessageDlg('Error',
Format('Project %s raised exception class %d with message ''%s''.', [Project1.Title, AExceptionID, AExceptionText]),
mtError,[mbOk],0);
end;
procedure TDebugManager.OnDebuggerOutput(Sender: TObject; const AText: String);
begin
if FDebugOutputDlg <> nil
then FDebugOutputDlg.AddText(AText);
end;
procedure TDebugManager.OnDebuggerChangeState(Sender: TObject);
const
// dsNone, dsIdle, dsStop, dsPause, dsRun, dsError
TOOLSTATEMAP: array[TDBGState] of TIDEToolStatus = (
// dsNone, dsIdle, dsStop, dsPause, dsRun, dsError
itNone, itNone, itNone, itDebugger, itDebugger, itDebugger
);
STATENAME: array[TDBGState] of string = (
'dsNone', 'dsIdle', 'dsStop', 'dsPause', 'dsRun', 'dsError'
);
begin
// Is the next line needed ???
if (Sender<>FDebugger) or (Sender=nil) then exit;
WriteLN('[TDebugManager.OnDebuggerChangeState] state: ', STATENAME[FDebugger.State]);
// All conmmands
// -------------------
// dcRun, dcPause, dcStop, dcStepOver, dcStepInto, dcRunTo, dcJumpto, dcBreak, dcWatch
// -------------------
with MainIDE do begin
// For run end step bypass idle, so we can set the filename later
RunSpeedButton.Enabled := (dcRun in FDebugger.Commands) or (FDebugger.State = dsIdle);
itmProjectRun.Enabled := RunSpeedButton.Enabled;
PauseSpeedButton.Enabled := dcPause in FDebugger.Commands;
itmProjectPause.Enabled := PauseSpeedButton.Enabled;
StepIntoSpeedButton.Enabled := (dcStepInto in FDebugger.Commands) or (FDebugger.State = dsIdle);
itmProjectStepInto.Enabled := StepIntoSpeedButton.Enabled;
StepOverSpeedButton.Enabled := (dcStepOver in FDebugger.Commands) or (FDebugger.State = dsIdle);
itmProjectStepOver.Enabled := StepOverSpeedButton.Enabled;
itmProjectRunToCursor.Enabled := dcRunTo in FDebugger.Commands;
itmProjectStop.Enabled := dcStop in FDebugger.Commands;;
// TODO: add other debugger menuitems
// TODO: implement by actions
ToolStatus := TOOLSTATEMAP[FDebugger.State];
end;
if FDebugger.State = dsError
then begin
WriteLN('Ooops, the debugger entered the error state');
end;
end;
procedure TDebugManager.OnDebuggerCurrentLine(Sender: TObject;
const ALocation: TDBGLocationRec);
// debugger paused program due to pause or error
// -> show the current execution line in editor
// if SrcLine = -1 then no source is available
var
ActiveSrcEdit: TSourceEditor;
UnitFile: String;
begin
if (Sender<>FDebugger) or (Sender=nil) then exit;
//TODO: Show assembler window if no source can be found.
if ALocation.SrcLine = -1 then Exit;
UnitFile := MainIDE.FindUnitFile(ALocation.SrcFile);
if UnitFile = ''
then UnitFile := ALocation.SrcFile;
if MainIDE.DoOpenEditorFile(UnitFile, [ofOnlyIfExists]) <> mrOk then exit;
ActiveSrcEdit := SourceNoteBook.GetActiveSE;
if ActiveSrcEdit=nil then exit;
with ActiveSrcEdit.EditorComponent do
begin
CaretXY:=Point(1, ALocation.SrcLine);
BlockBegin:=CaretXY;
BlockEnd:=CaretXY;
TopLine:=ALocation.SrcLine-(LinesInWindow div 2);
end;
ActiveSrcEdit.ErrorLine:=ALocation.SrcLine;
end;
//-----------------------------------------------------------------------------
// Debugger dialog routines
//-----------------------------------------------------------------------------
// Common handler
// The tag of the destroyed form contains the form variable pointing to it
procedure TDebugManager.DebugDialogDestroy(Sender: TObject);
begin
if TForm(Sender).Tag <> 0
then PPointer(TForm(Sender).Tag)^ := nil;
end;
procedure TDebugManager.ViewDebugDialog(const ADialogClass: TDebuggerDlgClass; var ADialog: TDebuggerDlg);
begin
if ADialog = nil
then begin
try
ADialog := ADialogClass.Create(Self);
except
on E: Exception do begin
WriteLN('[ERROR] IDE: Probably FPC bug #1888 caused an exception while creating class ''', ADialogClass.ClassName, '''');
WriteLN('[ERROR] IDE: Exception message: ', E.Message);
Exit;
end;
end;
ADialog.Tag := Integer(@ADialog);
ADialog.OnDestroy := @DebugDialogDestroy;
DoInitDebugger;
ADialog.Debugger := FDebugger;
end;
ADialog.Show;
ADialog.BringToFront;
end;
constructor TDebugManager.Create(TheOwner: TComponent);
begin
inherited Create(TheOwner);
DebugConstructor;
end;
destructor TDebugManager.Destroy;
begin
FreeThenNil(FDebugger);
FreeThenNil(FBreakPoints);
FreeThenNil(Watches_Dlg);
inherited Destroy;
end;
procedure TDebugManager.ConnectMainBarEvents;
begin
with MainIDE do begin
itmViewWatches.OnClick := @mnuViewWatchesClick;
itmViewBreakPoints.OnClick := @mnuViewBreakPointsClick;
itmViewLocals.OnClick := @mnuViewLocalsClick;
itmViewDebugOutput.OnClick := @mnuViewDebugOutputClick;
end;
end;
procedure TDebugManager.ConnectSourceNotebookEvents;
begin
SourceNotebook.OnAddWatchAtCursor := @OnSrcNotebookAddWatchesAtCursor;
SourceNotebook.OnCreateBreakPoint := @OnSrcNotebookCreateBreakPoint;
SourceNotebook.OnDeleteBreakPoint := @OnSrcNotebookDeleteBreakPoint;
end;
procedure TDebugManager.SetupMainBarShortCuts;
begin
with MainIDE, EditorOpts.KeyMap do
begin
itmViewWatches.ShortCut := CommandToShortCut(ecToggleWatches);
itmViewBreakpoints.ShortCut := CommandToShortCut(ecToggleBreakPoints);
itmViewDebugOutput.ShortCut := CommandToShortCut(ecToggleDebuggerOut);
itmViewLocals.ShortCut := CommandToShortCut(ecToggleLocals);
end;
end;
//-----------------------------------------------------------------------------
// Debugger routines
//-----------------------------------------------------------------------------
function TDebugManager.DoInitDebugger: TModalResult;
procedure ResetDialogs;
begin
if FDebugOutputDlg <> nil
then FDebugOutputDlg.Debugger := FDebugger;
if FBreakPointsDlg <> nil
then FBreakPointsDlg.Debugger := FDebugger;
if FLocalsDlg <> nil
then FLocalsDlg.Debugger := FDebugger;
end;
var
OldBreakpoints: TDBGBreakpoints;
LaunchingCmdLine, LaunchingApplication, LaunchingParams: String;
begin
WriteLN('[TDebugManager.DoInitDebugger] A');
Result:=mrCancel;
if Project1.MainUnit < 0 then Exit;
LaunchingCmdLine:=MainIDE.GetRunCommandLine;
SplitCmdLine(LaunchingCmdLine,LaunchingApplication,LaunchingParams);
OldBreakpoints := nil;
case EnvironmentOptions.DebuggerType of
dtGnuDebugger: begin
if (FDebugger <> nil)
and ( not(FDebugger is TGDBMIDebugger)
or (FDebugger.ExternalDebugger <> EnvironmentOptions.DebuggerFilename)
)
then begin
OldBreakpoints := TDBGBreakpoints.Create(nil, TDBGBreakpoint);
OldBreakpoints.Assign(FBreakPoints);
FBreakPoints := nil;
FDebugger.Free;
FDebugger := nil;
ResetDialogs;
end;
if FDebugger = nil
then begin
if FBreakPoints <> nil
then begin
OldBreakpoints := TDBGBreakpoints.Create(nil, TDBGBreakpoint);
OldBreakpoints.Assign(FBreakPoints);
end;
FDebugger := TGDBMIDebugger.Create(EnvironmentOptions.DebuggerFilename);
FBreakPoints := FDebugger.BreakPoints;
ResetDialogs;
end;
if OldBreakpoints <> nil
then FBreakPoints.Assign(OldBreakpoints);
end;
else
OldBreakpoints := FBreakPoints;
FBreakPoints := TDBGBreakpoints.Create(nil, TDBGBreakpoint);
FBreakPoints.Assign(OldBreakpoints);
FDebugger.Free;
FDebugger := nil;
ResetDialogs;
Exit;
end;
FDebugger.OnState:=@OnDebuggerChangeState;
FDebugger.OnCurrent:=@OnDebuggerCurrentLine;
FDebugger.OnDbgOutput := @OnDebuggerOutput;
FDebugger.OnException := @OnDebuggerException;
if FDebugger.State = dsNone
then FDebugger.Init;
FDebugger.FileName := LaunchingApplication;
FDebugger.Arguments := LaunchingParams;
if FDebugOutputDlg <> nil
then FDebugOutputDlg.Clear;
//TODO: Show/hide debug menuitems based on FDebugger.SupportedCommands
// property BreakPointGroups: TDBGBreakPointGroups read FBreakPointGroups; // list of all breakpoints
// property Watches: TDBGWatches read FWatches; // list of all watches localvars etc
Result := mrOk;
WriteLN('[TDebugManager.DoInitDebugger] END');
end;
// still part of main, should go here when dummydebugger is finished
//
//function TDebugManager.DoRunProject: TModalResult;
function TDebugManager.DoPauseProject: TModalResult;
begin
Result := mrCancel;
if (MainIDE.ToolStatus <> itDebugger)
or (FDebugger = nil)
then Exit;
FDebugger.Pause;
Result := mrOk;
end;
function TDebugManager.DoStepIntoProject: TModalResult;
begin
if (MainIDE.DoInitProjectRun <> mrOK)
or (MainIDE.ToolStatus <> itDebugger)
or (FDebugger = nil)
then begin
Result := mrAbort;
Exit;
end;
FDebugger.StepInto;
Result := mrOk;
end;
function TDebugManager.DoStepOverProject: TModalResult;
begin
if (MainIDE.DoInitProjectRun <> mrOK)
or (MainIDE.ToolStatus <> itDebugger)
or (FDebugger = nil)
then begin
Result := mrAbort;
Exit;
end;
FDebugger.StepOver;
Result := mrOk;
end;
function TDebugManager.DoStopProject: TModalResult;
begin
Result := mrCancel;
if (MainIDE.ToolStatus <> itDebugger)
or (FDebugger=nil)
then Exit;
FDebugger.Stop;
Result := mrOk;
end;
procedure TDebugManager.RunDebugger;
begin
if FDebugger <> nil then FDebugger.Run;
end;
procedure TDebugManager.EndDebugging;
begin
if FDebugger <> nil then FDebugger.Done;
end;
function TDebugManager.DoRunToCursor: TModalResult;
var
ActiveSrcEdit: TSourceEditor;
ActiveUnitInfo: TUnitInfo;
UnitFilename: string;
begin
if (MainIDE.DoInitProjectRun <> mrOK)
or (MainIDE.ToolStatus <> itDebugger)
or (FDebugger = nil)
then begin
Result := mrAbort;
Exit;
end;
Result := mrCancel;
MainIDE.GetCurrentUnit(ActiveSrcEdit, ActiveUnitInfo);
if (ActiveSrcEdit=nil) or (ActiveUnitInfo=nil)
then begin
MessageDlg('Run to failed','Please open a unit before run.',mtError,
[mbCancel],0);
Exit;
end;
if not ActiveUnitInfo.Source.IsVirtual
then UnitFilename:=ActiveUnitInfo.Filename
else UnitFilename:=MainIDE.GetTestUnitFilename(ActiveUnitInfo);
FDebugger.RunTo(ExtractFilename(UnitFilename), ActiveSrcEdit.EditorComponent.CaretY);
Result := mrOK;
end;
end.

View File

@ -5,52 +5,12 @@
{------------------------------------------------------------------------------}
{$IFDEF IDE_HEAD}
itmViewwatches: TMenuItem;
itmViewBreakpoints: TMenuItem;
itmViewLocals: TMenuItem;
itmViewDebugOutput: TMenuItem;
// Menu events
procedure mnuViewWatchesClick(Sender: TObject);
procedure mnuViewBreakPointsClick(Sender: TObject);
procedure mnuViewDebugOutputClick(Sender: TObject);
procedure mnuViewLocalsClick(Sender: TObject);
// SrcNotebook events
procedure OnSrcNotebookAddWatchesAtCursor(Sender: TObject);
procedure OnSrcNotebookCreateBreakPoint(Sender: TObject; Line: Integer);
procedure OnSrcNotebookDeleteBreakPoint(Sender: TObject; Line: Integer);
// Debugger events
procedure OnDebuggerChangeState(Sender: TObject);
procedure OnDebuggerCurrentLine(Sender: TObject; const ALocation: TDBGLocationRec);
procedure OnDebuggerOutput(Sender: TObject; const AText: String);
procedure OnDebuggerException(Sender: TObject; const AExceptionID: Integer; const AExceptionText: String);
{$ELSE} {$IFDEF IDE_PRIVATE}
FBreakPoints: TDBGBreakPoints; // Points to debugger breakpoints if available
// Else to own objet
FDebugOutputDlg: TDBGOutputForm;
FBreakPointsDlg: TBreakPointsDlg;
FLocalsDlg: TLocalsDlg;
FDebugger: TDebugger;
procedure DebugConstructor;
procedure DebugCreateShortCuts;
procedure DebugLoadMenus;
procedure DebugDialogDestroy(Sender: TObject);
procedure ViewDebugDialog(const ADialogClass: TDebuggerDlgClass; var ADialog: TDebuggerDlg);
{$ELSE} {$IFDEF IDE_PUBLIC}
function DoInitDebugger: TModalResult;
function DoPauseProject: TModalResult;
function DoStepIntoProject: TModalResult;
function DoStepOverProject: TModalResult;
function DoRunToCursor: TModalResult;
function DoStopProject: TModalResult;
{$ELSE} {$IFDEF IDE_IMPLEMENTATION}
//=============================================================================
@ -61,412 +21,6 @@
// IDE initialization
//-----------------------------------------------------------------------------
procedure TMainIDE.DebugConstructor;
begin
// TWatchesDlg
Watches_Dlg := TWatchesDlg.Create(Self);
FBreakPointsDlg := nil;
FLocalsDlg := nil;
FDebugger := nil;
FBreakPoints := TDBGBreakPoints.Create(nil, TDBGBreakPoint);
end;
procedure TMainIDE.DebugCreateShortCuts;
begin
with EditorOpts.KeyMap do
begin
itmViewWatches.ShortCut := CommandToShortCut(ecToggleWatches);
itmViewBreakpoints.ShortCut := CommandToShortCut(ecToggleBreakPoints);
itmViewDebugOutput.ShortCut := CommandToShortCut(ecToggleDebuggerOut);
itmViewLocals.ShortCut := CommandToShortCut(ecToggleLocals);
end;
end;
procedure TMainIDE.DebugLoadMenus;
begin
itmViewWatches := TMenuItem.Create(Self);
itmViewWatches.Name:='itmViewWatches';
itmViewWatches.Caption := 'Watches';
itmViewWatches.OnClick := @mnuViewWatchesClick;
itmViewDebugWindows.Add(itmViewWatches);
itmViewBreakPoints := TMenuItem.Create(Self);
itmViewBreakPoints.Name:='itmViewBreakPoints';
itmViewBreakPoints.Caption := 'BreakPoints';
itmViewBreakPoints.OnClick := @mnuViewBreakPointsClick;
itmViewDebugWindows.Add(itmViewBreakPoints);
itmViewLocals := TMenuItem.Create(Self);
itmViewLocals.Name:='itmViewLocals';
itmViewLocals.Caption := 'Local Variables';
itmViewLocals.OnClick := @mnuViewLocalsClick;
itmViewDebugWindows.Add(itmViewLocals);
itmViewDebugOutput := TMenuItem.Create(Self);
itmViewDebugOutput.Name:='itmViewDebugOutput';
itmViewDebugOutput.Caption := 'Debug output';
itmViewDebugOutput.OnClick := @mnuViewDebugOutputClick;
itmViewDebugWindows.Add(itmViewDebugOutput);
end;
//-----------------------------------------------------------------------------
// Menu events
//-----------------------------------------------------------------------------
procedure TMainIDE.mnuViewWatchesClick(Sender : TObject);
begin
Watches_dlg.Show;
end;
procedure TMainIDE.mnuViewBreakPointsClick(Sender : TObject);
begin
ViewDebugDialog(TBreakPointsDlg, FBreakPointsDlg);
end;
procedure TMainIDE.mnuViewDebugOutputClick(Sender : TObject);
begin
ViewDebugDialog(TDBGOutputForm, FDebugOutputDlg);
end;
procedure TMainIDE.mnuViewLocalsClick(Sender : TObject);
begin
ViewDebugDialog(TLocalsDlg, FLocalsDlg);
end;
//-----------------------------------------------------------------------------
// ScrNoteBook events
//-----------------------------------------------------------------------------
procedure TMainIDE.OnSrcNotebookAddWatchesAtCursor(Sender : TObject);
var
SE : TSourceEditor;
WatchVar: String;
NewWatch: TdbgWatch;
begin
if FDebugger = nil then Exit;
//get the sourceEditor.
SE := TSourceNotebook(sender).GetActiveSE;
if not Assigned(SE) then Exit;
WatchVar := SE.GetWordAtCurrentCaret;
if WatchVar = '' then Exit;
NewWatch := TdbgWatch(FDebugger.Watches.Add);
NewWatch.Expression := WatchVar;
NewWatch.Enabled := True;
end;
procedure TMainIDE.OnSrcNotebookCreateBreakPoint(Sender: TObject; Line: Integer);
var
NewBreak: TDBGBreakPoint;
begin
if SourceNotebook.Notebook = nil then Exit;
NewBreak := FBreakPoints.Add(ExtractFilename(TSourceNotebook(sender).GetActiveSe.FileName), Line);
NewBreak.Enabled := True;
end;
procedure TMainIDE.OnSrcNotebookDeleteBreakPoint(Sender: TObject; Line: Integer);
begin
if SourceNotebook.Notebook = nil then Exit;
FBreakPoints.Find(ExtractFilename(TSourceNotebook(sender).GetActiveSe.FileName), Line).Free;
end;
//-----------------------------------------------------------------------------
// Debugger events
//-----------------------------------------------------------------------------
procedure TMainIDE.OnDebuggerException(Sender: TObject; const AExceptionID: Integer; const AExceptionText: String);
begin
MessageDlg('Error',
Format('Project %s raised exception class %d with message ''%s''.', [Project1.Title, AExceptionID, AExceptionText]),
mtError,[mbOk],0);
end;
procedure TMainIDE.OnDebuggerOutput(Sender: TObject; const AText: String);
begin
if FDebugOutputDlg <> nil
then FDebugOutputDlg.AddText(AText);
end;
procedure TMainIDE.OnDebuggerChangeState(Sender: TObject);
const
// dsNone, dsIdle, dsStop, dsPause, dsRun, dsError
TOOLSTATEMAP: array[TDBGState] of TIDEToolStatus = (
// dsNone, dsIdle, dsStop, dsPause, dsRun, dsError
itNone, itNone, itNone, itDebugger, itDebugger, itDebugger
);
STATENAME: array[TDBGState] of string = (
'dsNone', 'dsIdle', 'dsStop', 'dsPause', 'dsRun', 'dsError'
);
begin
// Is the next line needed ???
if (Sender<>FDebugger) or (Sender=nil) then exit;
WriteLN('[TMainIDE.OnDebuggerChangeState] state: ', STATENAME[FDebugger.State]);
// All conmmands
// -------------------
// dcRun, dcPause, dcStop, dcStepOver, dcStepInto, dcRunTo, dcJumpto, dcBreak, dcWatch
// -------------------
// For run end step bypass idle, so we can set the filename later
RunSpeedButton.Enabled := (dcRun in FDebugger.Commands) or (FDebugger.State = dsIdle);
itmProjectRun.Enabled := RunSpeedButton.Enabled;
PauseSpeedButton.Enabled := dcPause in FDebugger.Commands;
itmProjectPause.Enabled := PauseSpeedButton.Enabled;
StepIntoSpeedButton.Enabled := (dcStepInto in FDebugger.Commands) or (FDebugger.State = dsIdle);
itmProjectStepInto.Enabled := StepIntoSpeedButton.Enabled;
StepOverSpeedButton.Enabled := (dcStepOver in FDebugger.Commands) or (FDebugger.State = dsIdle);
itmProjectStepOver.Enabled := StepOverSpeedButton.Enabled;
itmProjectRunToCursor.Enabled := dcRunTo in FDebugger.Commands;
itmProjectStop.Enabled := dcStop in FDebugger.Commands;;
// TODO: add other debugger menuitems
// TODO: implement by actions
ToolStatus := TOOLSTATEMAP[FDebugger.State];
if FDebugger.State = dsError
then begin
WriteLN('Ooops, the debugger entered the error state');
end;
end;
procedure TMainIDE.OnDebuggerCurrentLine(Sender: TObject;
const ALocation: TDBGLocationRec);
// debugger paused program due to pause or error
// -> show the current execution line in editor
// if SrcLine = -1 then no source is available
var
ActiveSrcEdit: TSourceEditor;
UnitFile: String;
begin
if (Sender<>FDebugger) or (Sender=nil) then exit;
//TODO: Show assembler window if no source can be found.
if ALocation.SrcLine = -1 then Exit;
UnitFile := FindUnitFile(ALocation.SrcFile);
if UnitFile = ''
then UnitFile := ALocation.SrcFile;
if DoOpenEditorFile(UnitFile, [ofOnlyIfExists]) <> mrOk then exit;
ActiveSrcEdit := SourceNoteBook.GetActiveSE;
if ActiveSrcEdit=nil then exit;
with ActiveSrcEdit.EditorComponent do
begin
CaretXY:=Point(1, ALocation.SrcLine);
BlockBegin:=CaretXY;
BlockEnd:=CaretXY;
TopLine:=ALocation.SrcLine-(LinesInWindow div 2);
end;
ActiveSrcEdit.ErrorLine:=ALocation.SrcLine;
end;
//-----------------------------------------------------------------------------
// Debugger dialog routines
//-----------------------------------------------------------------------------
// Common handler
// The tag of the destroyed form contains the form variable pointing to it
procedure TMainIDE.DebugDialogDestroy(Sender: TObject);
begin
if TForm(Sender).Tag <> 0
then PPointer(TForm(Sender).Tag)^ := nil;
end;
procedure TMainIDE.ViewDebugDialog(const ADialogClass: TDebuggerDlgClass; var ADialog: TDebuggerDlg);
begin
if ADialog = nil
then begin
try
ADialog := ADialogClass.Create(Self);
except
on E: Exception do begin
WriteLN('[ERROR] IDE: Probably FPC bug #1888 caused an exception while creating class ''', ADialogClass.ClassName, '''');
WriteLN('[ERROR] IDE: Exception message: ', E.Message);
Exit;
end;
end;
ADialog.Tag := Integer(@ADialog);
ADialog.OnDestroy := @DebugDialogDestroy;
DoInitDebugger;
ADialog.Debugger := FDebugger;
end;
ADialog.Show;
ADialog.BringToFront;
end;
//-----------------------------------------------------------------------------
// Debugger routines
//-----------------------------------------------------------------------------
function TMainIDE.DoInitDebugger: TModalResult;
procedure ResetDialogs;
begin
if FDebugOutputDlg <> nil
then FDebugOutputDlg.Debugger := FDebugger;
if FBreakPointsDlg <> nil
then FBreakPointsDlg.Debugger := FDebugger;
if FLocalsDlg <> nil
then FLocalsDlg.Debugger := FDebugger;
end;
var
OldBreakpoints: TDBGBreakpoints;
begin
WriteLN('[TMainIDE.DoInitDebugger] A');
Result:=mrCancel;
if Project1.MainUnit < 0 then Exit;
OldBreakpoints := nil;
case EnvironmentOptions.DebuggerType of
dtGnuDebugger: begin
if (FDebugger <> nil)
and ( not(FDebugger is TGDBMIDebugger)
or (FDebugger.ExternalDebugger <> EnvironmentOptions.DebuggerFilename)
)
then begin
OldBreakpoints := TDBGBreakpoints.Create(nil, TDBGBreakpoint);
OldBreakpoints.Assign(FBreakPoints);
FBreakPoints := nil;
FDebugger.Free;
FDebugger := nil;
ResetDialogs;
end;
if FDebugger = nil
then begin
if FBreakPoints <> nil
then begin
OldBreakpoints := TDBGBreakpoints.Create(nil, TDBGBreakpoint);
OldBreakpoints.Assign(FBreakPoints);
end;
FDebugger := TGDBMIDebugger.Create(EnvironmentOptions.DebuggerFilename);
FBreakPoints := FDebugger.BreakPoints;
ResetDialogs;
end;
if OldBreakpoints <> nil
then FBreakPoints.Assign(OldBreakpoints);
end;
else
OldBreakpoints := FBreakPoints;
FBreakPoints := TDBGBreakpoints.Create(nil, TDBGBreakpoint);
FBreakPoints.Assign(OldBreakpoints);
FDebugger.Free;
FDebugger := nil;
ResetDialogs;
Exit;
end;
FDebugger.OnState:=@OnDebuggerChangeState;
FDebugger.OnCurrent:=@OnDebuggerCurrentLine;
FDebugger.OnDbgOutput := @OnDebuggerOutput;
FDebugger.OnException := @OnDebuggerException;
if FDebugger.State = dsNone
then FDebugger.Init;
//TODO: Show/hide debug menuitems based on FDebugger.SupportedCommands
// property BreakPointGroups: TDBGBreakPointGroups read FBreakPointGroups; // list of all breakpoints
// property Watches: TDBGWatches read FWatches; // list of all watches localvars etc
Result := mrOk;
WriteLN('[TMainIDE.DoInitDebugger] END');
end;
// still part of main, should go here when dummydebugger is finished
//
//function TMainIDE.DoRunProject: TModalResult;
function TMainIDE.DoPauseProject: TModalResult;
begin
Result := mrCancel;
if (ToolStatus <> itDebugger)
or (FDebugger = nil)
then Exit;
FDebugger.Pause;
Result := mrOk;
end;
function TMainIDE.DoStepIntoProject: TModalResult;
begin
if (DoInitProjectRun <> mrOK)
or (ToolStatus <> itDebugger)
or (FDebugger = nil)
then begin
Result := mrAbort;
Exit;
end;
FDebugger.StepInto;
Result := mrOk;
end;
function TMainIDE.DoStepOverProject: TModalResult;
begin
if (DoInitProjectRun <> mrOK)
or (ToolStatus <> itDebugger)
or (FDebugger = nil)
then begin
Result := mrAbort;
Exit;
end;
FDebugger.StepOver;
Result := mrOk;
end;
function TMainIDE.DoStopProject: TModalResult;
begin
Result := mrCancel;
if (ToolStatus <> itDebugger)
or (FDebugger=nil)
then Exit;
FDebugger.Stop;
Result := mrOk;
end;
function TMainIDE.DoRunToCursor: TModalResult;
var
ActiveSrcEdit: TSourceEditor;
ActiveUnitInfo: TUnitInfo;
UnitFilename: string;
begin
if (DoInitProjectRun <> mrOK)
or (ToolStatus <> itDebugger)
or (FDebugger = nil)
then begin
Result := mrAbort;
Exit;
end;
Result := mrCancel;
GetCurrentUnit(ActiveSrcEdit, ActiveUnitInfo);
if (ActiveSrcEdit=nil) or (ActiveUnitInfo=nil)
then begin
MessageDlg('Run to failed','Please open a unit before run.',mtError,
[mbCancel],0);
Exit;
end;
if not ActiveUnitInfo.Source.IsVirtual
then UnitFilename:=ActiveUnitInfo.Filename
else UnitFilename:=GetTestUnitFilename(ActiveUnitInfo);
FDebugger.RunTo(ExtractFilename(UnitFilename), ActiveSrcEdit.EditorComponent.CaretY);
Result := mrOK;
end;

View File

@ -42,14 +42,10 @@ uses
Debugger, DBGOutputForm, GDBMIDebugger, RunParamsOpts, ExtToolDialog,
MacroPromptDlg, LMessages, ProjectDefs, Watchesdlg, BreakPointsdlg, ColumnDlg,
OutputFilter, BuildLazDialog, MiscOptions, EditDefineTree, CodeToolsOptions,
TypInfo, IDEOptionDefs, CodeToolsDefines, LocalsDlg, DebuggerDlg, MainBar;
TypInfo, IDEOptionDefs, CodeToolsDefines, LocalsDlg, DebuggerDlg,
BaseDebugManager, DebugManager, MainBar;
type
{$DEFINE IDE_TYPE}
{$I ide_debugger.inc}
{$UNDEF IDE_TYPE}
TMainIDE = class(TMainIDEBar)
// event handlers
//procedure FormShow(Sender : TObject);
@ -201,10 +197,6 @@ type
var Abort: boolean);
procedure OnExtToolFreeOutputFilter(OutputFilter: TOutputFilter;
ErrorOccurred: boolean);
{$DEFINE IDE_HEAD}
{$I ide_debugger.inc}
{$UNDEF IDE_HEAD}
private
FHintSender : TObject;
FCodeLastActivated : Boolean; // used for toggling between code and forms
@ -221,9 +213,6 @@ type
function CreateSeperator : TMenuItem;
procedure SetDefaultsForForm(aForm : TCustomForm);
{$DEFINE IDE_PRIVATE}
{$I ide_debugger.inc}
{$UNDEF IDE_PRIVATE}
protected
procedure ToolButtonClick(Sender : TObject);
procedure OnApplyWindowLayout(ALayout: TIDEWindowLayout);
@ -243,7 +232,7 @@ type
procedure SetupToolsMenu;
procedure SetupEnvironmentMenu;
procedure SetupHelpMenu;
procedure ConnectFormEvents;
procedure ConnectMainBarEvents;
procedure LoadMenuShortCuts;
procedure SetupSpeedButtons;
procedure SetupComponentNoteBook;
@ -293,9 +282,7 @@ type
function DoCompleteLoadingProjectInfo: TModalResult;
public
ToolStatus: TIDEToolStatus;
constructor Create(AOwner: TComponent); override;
constructor Create(TheOwner: TComponent); override;
destructor Destroy; override;
// files/units
@ -306,7 +293,7 @@ type
function DoCloseEditorUnit(PageIndex:integer;
SaveFirst: boolean):TModalResult;
function DoOpenEditorFile(const AFileName:string;
Flags: TOpenFlags): TModalResult;
Flags: TOpenFlags): TModalResult; override;
function DoOpenFileAtCursor(Sender: TObject):TModalResult;
function DoSaveAll: TModalResult;
function DoOpenMainUnit(ProjectLoading: boolean): TModalResult;
@ -320,7 +307,7 @@ type
function DoAddActiveUnitToProject: TModalResult;
function DoRemoveFromProjectDialog: TModalResult;
function DoBuildProject(BuildAll: boolean): TModalResult;
function DoInitProjectRun: TModalResult;
function DoInitProjectRun: TModalResult; override;
function DoRunProject: TModalResult;
function SomethingOfProjectIsModified: boolean;
function DoCreateProjectForProgram(ProgramBuf: TCodeBuffer): TModalResult;
@ -335,13 +322,13 @@ type
// useful methods
procedure GetCurrentUnit(var ActiveSourceEditor:TSourceEditor;
var ActiveUnitInfo:TUnitInfo);
var ActiveUnitInfo:TUnitInfo); override;
procedure DoSwitchToFormSrc(var ActiveSourceEditor:TSourceEditor;
var ActiveUnitInfo:TUnitInfo);
procedure GetUnitWithPageIndex(PageIndex:integer;
var ActiveSourceEditor:TSourceEditor; var ActiveUnitInfo:TUnitInfo);
function GetSourceEditorForUnitInfo(AnUnitInfo: TUnitInfo): TSourceEditor;
function FindUnitFile(const AFilename: string): string;
function FindUnitFile(const AFilename: string): string; override;
function DoSaveStreamToFile(AStream:TStream; const Filename:string;
IsPartOfProject:boolean): TModalResult;
function DoLoadMemoryStreamFromFile(MemStream: TMemoryStream;
@ -382,8 +369,8 @@ type
procedure DoArrangeSourceEditorAndMessageView;
function GetProjectTargetFilename: string;
function GetTestProjectFilename: string;
function GetTestUnitFilename(AnUnitInfo: TUnitInfo): string;
function GetRunCommandLine: string;
function GetTestUnitFilename(AnUnitInfo: TUnitInfo): string; override;
function GetRunCommandLine: string; override;
procedure OnMacroSubstitution(TheMacro: TTransferMacro; var s:string;
var Handled, Abort: boolean);
function OnMacroPromptFunction(const s:string; var Abort: boolean):string;
@ -412,10 +399,6 @@ type
procedure SaveEnvironment;
procedure LoadDesktopSettings(TheEnvironmentOptions: TEnvironmentOptions);
procedure SaveDesktopSettings(TheEnvironmentOptions: TEnvironmentOptions);
{$DEFINE IDE_PUBLIC}
{$I ide_debugger.inc}
{$UNDEF IDE_PUBLIC}
end;
@ -574,9 +557,10 @@ begin
end;
end;
constructor TMainIDE.Create(AOwner: TComponent);
constructor TMainIDE.Create(TheOwner: TComponent);
begin
inherited Create(AOwner);
MainIDE:=Self;
inherited Create(TheOwner);
// load options
ParseCmdLineOptions;
@ -597,10 +581,14 @@ begin
SetupMainMenu;
SetupSpeedButtons;
SetupComponentNoteBook;
ConnectFormEvents;
ConnectMainBarEvents;
SetupHints;
end;
DebugBoss:=TDebugManager.Create(Self);
DebugBoss.ConnectMainBarEvents;
LoadMenuShortCuts;
SetupComponentTabs;
SetupOutputFilter;
SetupCompilerInterface;
@ -608,9 +596,8 @@ begin
SetupFormEditor;
SetupSourceNotebook;
SetupTransferMacros;
DebugConstructor;
SetupControlSelection;
SetupStartProject;
end;
@ -618,10 +605,9 @@ destructor TMainIDE.Destroy;
begin
writeln('[TMainIDE.Destroy] A');
{$IFDEF IDE_MEM_CHECK}CheckHeap(IntToStr(GetMem_Cnt));{$ENDIF}
if FDebugger <> nil then FDebugger.Done;
DebugBoss.EndDebugging;
FreeThenNil(Project1);
FreeThenNil(FBreakPoints);
if TheControlSelection<>nil then begin
TheControlSelection.OnChange:=nil;
FreeThenNil(TheControlSelection);
@ -637,8 +623,6 @@ writeln('[TMainIDE.Destroy] A');
FreeThenNil(EnvironmentOptions);
FreeThenNil(HintTimer1);
FreeThenNil(HintWindow1);
FreeThenNil(Watches_Dlg);
FreeThenNil(FDebugger);
writeln('[TMainIDE.Destroy] B -> inherited Destroy...');
{$IFDEF IDE_MEM_CHECK}CheckHeap(IntToStr(GetMem_Cnt));{$ENDIF}
@ -959,9 +943,7 @@ begin
SourceNotebook.OnShowUnitInfo := @OnSrcNoteBookShowUnitInfo;
SourceNotebook.OnToggleFormUnitClicked := @OnSrcNotebookToggleFormUnit;
SourceNotebook.OnViewJumpHistory := @OnSrcNotebookViewJumpHistory;
SourceNotebook.OnAddWatchAtCursor := @OnSrcNotebookAddWatchesAtCursor;
SourceNotebook.OnCreateBreakPoint := @OnSrcNotebookCreateBreakPoint;
SourceNotebook.OnDeleteBreakPoint := @OnSrcNotebookDeleteBreakPoint;
DebugBoss.ConnectSourceNotebookEvents;
// connect search menu to sourcenotebook
itmSearchFind.OnClick := @SourceNotebook.FindClicked;
@ -1118,9 +1100,6 @@ begin
SetupToolsMenu;
SetupEnvironmentMenu;
SetupHelpMenu;
DebugLoadMenus;
LoadMenuShortCuts;
end;
procedure TMainIDE.AddRecentSubMenu(ParentMenuItem: TMenuItem;
@ -1395,6 +1374,26 @@ begin
itmViewDebugWindows.Name := 'itmViewDebugWindows';
itmViewDebugWindows.Caption := 'Debug windows';
mnuView.Add(itmViewDebugWindows);
itmViewWatches := TMenuItem.Create(Self);
itmViewWatches.Name:='itmViewWatches';
itmViewWatches.Caption := 'Watches';
itmViewDebugWindows.Add(itmViewWatches);
itmViewBreakPoints := TMenuItem.Create(Self);
itmViewBreakPoints.Name:='itmViewBreakPoints';
itmViewBreakPoints.Caption := 'BreakPoints';
itmViewDebugWindows.Add(itmViewBreakPoints);
itmViewLocals := TMenuItem.Create(Self);
itmViewLocals.Name:='itmViewLocals';
itmViewLocals.Caption := 'Local Variables';
itmViewDebugWindows.Add(itmViewLocals);
itmViewDebugOutput := TMenuItem.Create(Self);
itmViewDebugOutput.Name:='itmViewDebugOutput';
itmViewDebugOutput.Caption := 'Debug output';
itmViewDebugWindows.Add(itmViewDebugOutput);
end;
procedure TMainIDE.SetupProjectMenu;
@ -1599,7 +1598,7 @@ begin
mnuHelp.Add(itmHelpAboutLazarus);
end;
procedure TMainIDE.ConnectFormEvents;
procedure TMainIDE.ConnectMainBarEvents;
begin
//OnShow := @FormShow;
OnClose := @FormClose;
@ -1807,11 +1806,11 @@ begin
ecBuildAll: DoBuildProject(Command=ecBuildAll);
ecRun: DoRunProject;
ecPause: DoPauseProject;
ecStepInto: DoStepIntoProject;
ecStepOver: DoStepOverProject;
ecRunToCursor: DoRunToCursor;
ecStopProgram: DoStopProject;
ecPause: DebugBoss.DoPauseProject;
ecStepInto: DebugBoss.DoStepIntoProject;
ecStepOver: DebugBoss.DoStepOverProject;
ecRunToCursor: DebugBoss.DoRunToCursor;
ecStopProgram: DebugBoss.DoStopProject;
ecFindProcedureDefinition,ecFindProcedureMethod:
DoJumpToProcedureSection;
@ -2033,27 +2032,27 @@ end;
Procedure TMainIDE.mnuPauseProjectClicked(Sender : TObject);
begin
DoPauseProject;
DebugBoss.DoPauseProject;
end;
Procedure TMainIDE.mnuStepIntoProjectClicked(Sender : TObject);
begin
DoStepIntoProject;
DebugBoss.DoStepIntoProject;
end;
Procedure TMainIDE.mnuStepOverProjectClicked(Sender : TObject);
begin
DoStepOverProject;
DebugBoss.DoStepOverProject;
end;
Procedure TMainIDE.mnuRunToCursorProjectClicked(Sender : TObject);
begin
DoRunToCursor;
DebugBoss.DoRunToCursor;
end;
Procedure TMainIDE.mnuStopProjectClicked(Sender : TObject);
begin
DoStopProject;
DebugBoss.DoStopProject;
end;
procedure TMainIDE.mnuProjectCompilerSettingsClicked(Sender : TObject);
@ -2402,7 +2401,8 @@ function TMainIDE.DoShowSaveFileAsDialog(AnUnitInfo: TUnitInfo;
var
SaveDialog: TSaveDialog;
SaveAsFilename, SaveAsFileExt, NewFilename, NewUnitName, NewFilePath,
NewResFilename, NewResFilePath, OldFilePath, NewPageName: string;
NewResFilename, NewResFilePath, OldFilePath, NewPageName,
NewLFMFilename: string;
ACaption, AText: string;
SrcEdit: TSourceEditor;
NewSource: TCodeBuffer;
@ -2502,9 +2502,10 @@ begin
if AnUnitInfo.FormName='' then begin
// unit has no form
// -> remove lfm file, so that it will not be auto loaded on next open
NewResFilename:=ChangeFileExt(NewFilename,'.lfm');
if (not DeleteFile(NewResFilename))
and (MessageDlg('Delete failed','Deleting of file "'+NewResFilename+'"'
NewLFMFilename:=ChangeFileExt(NewFilename,'.lfm');
if (FileExists(NewLFMFilename))
and (not DeleteFile(NewLFMFilename))
and (MessageDlg('Delete failed','Deleting of file "'+NewLFMFilename+'"'
+' failed.',mtError,[mbIgnore,mbCancel],0)=mrCancel) then
begin
Result:=mrCancel;
@ -4351,10 +4352,9 @@ end;
function TMainIDE.DoInitProjectRun: TModalResult;
var
ProgramFilename, LaunchingCmdLine, LaunchingApplication,
LaunchingParams: String;
ProgramFilename: String;
begin
if ToolStatus = itDebugger
if ToolStatus <> itNone
then begin
// already running so no initialization needed
Result := mrOk;
@ -4382,17 +4382,12 @@ begin
[mbCancel], 0);
Exit;
end;
LaunchingCmdLine:=GetRunCommandLine;
// Setup debugger
case EnvironmentOptions.DebuggerType of
dtGnuDebugger: begin
if (FDebugger = nil)
and (DoInitDebugger <> mrOk)
if (DebugBoss.DoInitDebugger <> mrOk)
then Exit;
SplitCmdLine(LaunchingCmdLine,LaunchingApplication,LaunchingParams);
FDebugger.FileName := LaunchingApplication;
FDebugger.Arguments := LaunchingParams;
// ToDo: set working directory
end;
else
@ -4400,7 +4395,7 @@ begin
try
CheckIfFileIsExecutable(ProgramFilename);
FRunProcess := TProcess.Create(nil);
FRunProcess.CommandLine := LaunchingCmdLine;
FRunProcess.CommandLine := GetRunCommandLine;
FRunProcess.CurrentDirectory:=
Project1.RunParameterOptions.WorkingDirectory;
FRunProcess.Options:= [poNoConsole];
@ -4413,9 +4408,6 @@ begin
end;
end;
if FDebugOutputDlg <> nil
then FDebugOutputDlg.Clear;
Result := mrOK;
ToolStatus := itDebugger;
end;
@ -4433,13 +4425,10 @@ begin
Result := mrCancel;
case EnvironmentOptions.DebuggerType of
dtGnuDebugger: begin
if FDebugger = nil then Exit;
FDebugger.Run;
Result := mrOK;
end;
else
if EnvironmentOptions.DebuggerType <> dtNone then begin
DebugBoss.RunDebugger;
Result := mrOK;
end else begin
if FRunProcess = nil then Exit;
try
Writeln(' EXECUTING "',FRunProcess.CommandLine,'"');
@ -6148,7 +6137,7 @@ begin
itmHelpAboutLazarus.ShortCut:=CommandToShortCut(ecAboutLazarus);
end;
DebugCreateShortCuts;
DebugBoss.SetupMainBarShortCuts;
end;
procedure TMainIDE.mnuSearchFindBlockOtherEnd(Sender: TObject);
@ -6185,6 +6174,9 @@ end.
{ =============================================================================
$Log$
Revision 1.259 2002/03/27 10:39:42 lazarus
MG: splitted main.pp: debugger management in TDebugManager
Revision 1.258 2002/03/27 09:25:31 lazarus
MG: renamed main Project to Project1

View File

@ -138,6 +138,10 @@ type
itmViewForms : TMenuItem;
itmViewMessage : TMenuItem;
itmViewDebugWindows: TMenuItem;
itmViewwatches: TMenuItem;
itmViewBreakpoints: TMenuItem;
itmViewLocals: TMenuItem;
itmViewDebugOutput: TMenuItem;
itmProjectNew: TMenuItem;
itmProjectOpen: TMenuItem;
@ -178,7 +182,18 @@ type
HintTimer1 : TTimer;
HintWindow1 : THintWindow;
public
ToolStatus: TIDEToolStatus;
function FindUnitFile(const AFilename: string): string; virtual; abstract;
procedure GetCurrentUnit(var ActiveSourceEditor:TSourceEditor;
var ActiveUnitInfo:TUnitInfo); virtual; abstract;
function GetTestUnitFilename(AnUnitInfo: TUnitInfo): string; virtual; abstract;
function GetRunCommandLine: string; virtual; abstract;
function DoOpenEditorFile(const AFileName:string;
Flags: TOpenFlags): TModalResult; virtual; abstract;
function DoInitProjectRun: TModalResult; virtual; abstract;
end;
var