View Issue Details

IDProjectCategoryView StatusLast Update
0022539PatchesIDEpublic2012-07-31 13:23
ReporterBigChimpAssigned ToMattias Gaertner 
PrioritynormalSeverityfeatureReproducibilitysometimes
Status closedResolutionfixed 
Platformx64OSWindowsOS VersionVista
Product Version1.1 (SVN)Product Build38091 
Target VersionFixed in Version 
Summary0022539: [Patch] Setup/initial dialog: check for debugger and make check in GUI instead of silently changing config
DescriptionFurther checking in --setup dialog:

Added GUI checks for valid make location (instead of silently changing settings)

Added GUI checks for valid debugger location (similarly to the existing make checks), including
- primary config path
- secondary config path
- searching in current default Lazarus installer location
- searching for proposed new Windows installer in issue 22533 (that uses targetos/targetcpu macros). Even if 22533 is not implemented, this searching will not harm users
- searching in fpc bin directory
- searching in history
- searching in path

Changed sddqIncomplete image from error to warning (e.g. happens when make.exe not in fpc bin dir, as e.g. happens in default fpcup installs): the configuration can still work, but is not certain to work. Showing an error would be too harsh.
Steps To ReproduceTested on Win32 Lazarus with debugger set up as in issue 22533. Works.
Additional InformationRelated to (and parent of: that issue needs this patch): 22533: [Patch] Set up windows installer to allow multiple debuggers using $(TargetCPU)-$(TargetOS)

Don't know why widths & heights change => presumably due to using Laz 1.1 instead of older versions? In any case, I did not change widths and heights manually.
Tagscheck, debugger, gdb, make, setup
Fixed in Revision
LazTarget-
WidgetsetWin32/Win64
Attached Files
  • initial_checkdebugger.diff (34,233 bytes)
    Index: ide/lazarusidestrconsts.pas
    ===================================================================
    --- ide/lazarusidestrconsts.pas	(revision 38091)
    +++ ide/lazarusidestrconsts.pas	(working copy)
    @@ -2008,6 +2008,7 @@
       dlgCOLibraries = 'Libraries (-Fl):';
       dlgCODebugPath = 'Debugger path addition (none):';
       lisCompiler = 'Compiler';
    +  lisDebugger = 'Debugger';
       lisToFPCPath = 'Path:';
       lisCOSkipCallingCompiler = 'Skip calling compiler';
       lisCOAmbiguousAdditionalCompilerConfigFile = 'Ambiguous additional compiler '
    @@ -5437,6 +5438,10 @@
         +'Lazarus directory you will get a lot of warnings.';
       lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW = 'Without a proper '
         +'compiler the code browsing and compiling will be disappointing.';
    +  lisWithoutAProperDebuggerDebuggingWillBeDisappointing = 'Without a proper '
    +    +'debugger, debugging will be disappointing.';
    +  lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp = 'Without a proper '
    +    +'make executable the code browsing and compiling will be disappointing.';
       lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio = 'Without the proper '
         +'FPC sources code browsing and completion will be very limited.';
       lisTheLazarusDirectoryContainsTheSourcesOfTheIDEAndTh = 'The Lazarus '
    @@ -5446,6 +5451,11 @@
       lisTheFreePascalCompilerExecutableTypicallyHasTheName = 'The Free Pascal '
         +'compiler executable typically has the name "%s". You can also use the '
         +'target specific compiler like "%s". Please give the full file path.';
    +  lisTheMakeExecutableTypicallyHasTheName = 'The make executable typically '
    +    +'has the name "%s". Please give the full file path.';
    +  lisTheDebuggerExecutableTypicallyHasTheName = 'The debugger executable '
    +    +'typically has the name "%s". Pleae give the full file path. '
    +    +'A useful setting on Windows systems is: $(LazarusDir)\mingw\bin\$(TargetCPU)-$(TargetOS)\gdb.exe';
       lisFoundVersionExpected = 'Found version %s, expected %s';
       lisInvalidVersionIn = 'invalid version in %s';
       lisWrongVersionIn = 'wrong version in %s: %s';
    Index: ide/initialsetupdlgs.lfm
    ===================================================================
    --- ide/initialsetupdlgs.lfm	(revision 38091)
    +++ ide/initialsetupdlgs.lfm	(working copy)
    @@ -1,8 +1,8 @@
     object InitialSetupDialog: TInitialSetupDialog
       AnchorSideBottom.Side = asrBottom
    -  Left = 253
    +  Left = 319
       Height = 385
    -  Top = 253
    +  Top = 238
       Width = 620
       Caption = 'InitialSetupDialog'
       ClientHeight = 385
    @@ -10,7 +10,7 @@
       OnCreate = FormCreate
       OnDestroy = FormDestroy
       Position = poScreenCenter
    -  LCLVersion = '0.9.31'
    +  LCLVersion = '1.1'
       object PropertiesTreeView: TTreeView
         AnchorSideLeft.Control = Owner
         AnchorSideTop.Control = WelcomePaintBox
    @@ -18,7 +18,7 @@
         AnchorSideRight.Control = Splitter1
         AnchorSideBottom.Control = BtnPanel
         Left = 6
    -    Height = 289
    +    Height = 286
         Top = 54
         Width = 159
         Anchors = [akTop, akLeft, akRight, akBottom]
    @@ -40,7 +40,7 @@
         AnchorSideBottom.Control = PropertiesTreeView
         AnchorSideBottom.Side = asrBottom
         Left = 165
    -    Height = 289
    +    Height = 286
         Top = 54
         Width = 5
         Align = alNone
    @@ -48,21 +48,21 @@
       end
       object BtnPanel: TPanel
         Left = 10
    -    Height = 22
    -    Top = 353
    +    Height = 25
    +    Top = 350
         Width = 600
         Align = alBottom
         AutoSize = True
         BorderSpacing.Around = 10
         BevelOuter = bvNone
    -    ClientHeight = 22
    +    ClientHeight = 25
         ClientWidth = 600
         TabOrder = 2
         object StartIDEBitBtn: TBitBtn
    -      Left = 489
    -      Height = 22
    +      Left = 500
    +      Height = 25
           Top = 0
    -      Width = 111
    +      Width = 100
           Align = alRight
           AutoSize = True
           Caption = 'StartIDEBitBtn'
    @@ -80,13 +80,13 @@
         AnchorSideBottom.Control = Splitter1
         AnchorSideBottom.Side = asrBottom
         Left = 170
    -    Height = 289
    +    Height = 286
         Top = 54
         Width = 444
    -    ActivePage = FPCSourcesTabSheet
    +    ActivePage = LazarusTabSheet
         Anchors = [akTop, akLeft, akRight, akBottom]
         BorderSpacing.Right = 6
    -    TabIndex = 2
    +    TabIndex = 0
         TabOrder = 3
         OnChange = PropertiesPageControlChange
         Options = [nboHidePageListPopup]
    @@ -96,11 +96,11 @@
           ChildSizing.TopBottomSpacing = 6
           ChildSizing.HorizontalSpacing = 6
           ChildSizing.VerticalSpacing = 6
    -      ClientHeight = 255
    -      ClientWidth = 442
    +      ClientHeight = 258
    +      ClientWidth = 436
           object LazDirLabel: TLabel
             Left = 6
    -        Height = 14
    +        Height = 15
             Top = 6
             Width = 424
             Align = alTop
    @@ -115,11 +115,11 @@
             AnchorSideRight.Control = LazarusTabSheet
             AnchorSideRight.Side = asrBottom
             Left = 6
    -        Height = 21
    -        Top = 26
    +        Height = 23
    +        Top = 27
             Width = 424
             Anchors = [akTop, akLeft, akRight]
    -        ItemHeight = 0
    +        ItemHeight = 15
             OnChange = LazDirComboBoxChange
             TabOrder = 0
             Text = 'LazDirComboBox'
    @@ -128,8 +128,8 @@
             AnchorSideTop.Control = LazDirBrowseButton
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 174
    -        Top = 82
    +        Height = 165
    +        Top = 87
             Width = 424
             Align = alBottom
             Anchors = [akTop, akLeft, akRight, akBottom]
    @@ -148,9 +148,9 @@
             AnchorSideTop.Side = asrBottom
             AnchorSideRight.Side = asrBottom
             Left = 6
    -        Height = 23
    -        Top = 53
    -        Width = 122
    +        Height = 25
    +        Top = 56
    +        Width = 132
             AutoSize = True
             Caption = 'LazDirBrowseButton'
             OnClick = LazDirBrowseButtonClick
    @@ -163,13 +163,13 @@
           ChildSizing.TopBottomSpacing = 6
           ChildSizing.HorizontalSpacing = 6
           ChildSizing.VerticalSpacing = 6
    -      ClientHeight = 250
    -      ClientWidth = 438
    +      ClientHeight = 258
    +      ClientWidth = 436
           object CompilerLabel: TLabel
             Left = 6
    -        Height = 17
    +        Height = 15
             Top = 6
    -        Width = 426
    +        Width = 424
             Align = alTop
             Caption = 'CompilerLabel'
             ParentColor = False
    @@ -182,11 +182,11 @@
             AnchorSideRight.Control = CompilerTabSheet
             AnchorSideRight.Side = asrBottom
             Left = 6
    -        Height = 21
    -        Top = 29
    -        Width = 426
    +        Height = 23
    +        Top = 27
    +        Width = 424
             Anchors = [akTop, akLeft, akRight]
    -        ItemHeight = 0
    +        ItemHeight = 15
             OnChange = CompilerComboBoxChange
             TabOrder = 0
             Text = 'CompilerComboBox'
    @@ -196,9 +196,9 @@
             AnchorSideTop.Control = CompilerComboBox
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 20
    +        Height = 25
             Top = 56
    -        Width = 168
    +        Width = 149
             AutoSize = True
             Caption = 'CompilerBrowseButton'
             OnClick = CompilerBrowseButtonClick
    @@ -213,9 +213,9 @@
             AnchorSideBottom.Control = CompilerTabSheet
             AnchorSideBottom.Side = asrBottom
             Left = 6
    -        Height = 162
    -        Top = 82
    -        Width = 426
    +        Height = 165
    +        Top = 87
    +        Width = 424
             Anchors = [akTop, akLeft, akRight, akBottom]
             Lines.Strings = (
               'CompilerMemo'
    @@ -232,13 +232,13 @@
           ChildSizing.TopBottomSpacing = 6
           ChildSizing.HorizontalSpacing = 6
           ChildSizing.VerticalSpacing = 6
    -      ClientHeight = 250
    -      ClientWidth = 438
    +      ClientHeight = 258
    +      ClientWidth = 436
           object FPCSrcDirLabel: TLabel
             Left = 6
    -        Height = 17
    +        Height = 15
             Top = 6
    -        Width = 426
    +        Width = 424
             Align = alTop
             Caption = 'FPCSrcDirLabel'
             ParentColor = False
    @@ -246,11 +246,11 @@
           end
           object FPCSrcDirComboBox: TComboBox
             Left = 6
    -        Height = 21
    -        Top = 29
    -        Width = 426
    +        Height = 23
    +        Top = 27
    +        Width = 424
             Align = alTop
    -        ItemHeight = 0
    +        ItemHeight = 15
             OnChange = FPCSrcDirComboBoxChange
             TabOrder = 0
             Text = 'FPCSrcDirComboBox'
    @@ -260,9 +260,9 @@
             AnchorSideTop.Control = FPCSrcDirComboBox
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 20
    +        Height = 25
             Top = 56
    -        Width = 171
    +        Width = 152
             AutoSize = True
             Caption = 'FPCSrcDirBrowseButton'
             OnClick = FPCSrcDirBrowseButtonClick
    @@ -272,9 +272,9 @@
             AnchorSideTop.Control = FPCSrcDirBrowseButton
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 162
    -        Top = 82
    -        Width = 426
    +        Height = 165
    +        Top = 87
    +        Width = 424
             Align = alBottom
             Anchors = [akTop, akLeft, akRight, akBottom]
             Lines.Strings = (
    @@ -286,6 +286,118 @@
             TabOrder = 2
           end
         end
    +    object MakeExeTabSheet: TTabSheet
    +      Caption = 'MakeExeTabSheet'
    +      ClientHeight = 258
    +      ClientWidth = 436
    +      object MakeExeComboBox: TComboBox
    +        Left = 0
    +        Height = 23
    +        Top = 15
    +        Width = 436
    +        Align = alTop
    +        ItemHeight = 15
    +        OnChange = MakeExeComboBoxChange
    +        TabOrder = 0
    +        Text = 'MakeExeComboBox'
    +      end
    +      object MakeExeLabel: TLabel
    +        Left = 0
    +        Height = 15
    +        Top = 0
    +        Width = 436
    +        Align = alTop
    +        Caption = 'MakeExeLabel'
    +        ParentColor = False
    +        WordWrap = True
    +      end
    +      object MakeExeBrowseButton: TButton
    +        AnchorSideLeft.Control = FPCSourcesTabSheet
    +        AnchorSideTop.Control = MakeExeComboBox
    +        AnchorSideTop.Side = asrBottom
    +        Left = 6
    +        Height = 25
    +        Top = 38
    +        Width = 146
    +        AutoSize = True
    +        Caption = 'MakeExeBrowseButton'
    +        OnClick = MakeExeBrowseButtonClick
    +        TabOrder = 1
    +      end
    +      object MakeExeMemo: TMemo
    +        AnchorSideTop.Control = MakeExeBrowseButton
    +        AnchorSideTop.Side = asrBottom
    +        Left = 0
    +        Height = 195
    +        Top = 63
    +        Width = 436
    +        Align = alBottom
    +        Anchors = [akTop, akLeft, akRight, akBottom]
    +        Lines.Strings = (
    +          'FPCSrcDirMemo'
    +          ''
    +          ''
    +        )
    +        ReadOnly = True
    +        TabOrder = 2
    +      end
    +    end
    +    object DebuggerTabSheet: TTabSheet
    +      Caption = 'DebuggerTabSheet'
    +      ClientHeight = 258
    +      ClientWidth = 436
    +      object DebuggerComboBox: TComboBox
    +        Left = 0
    +        Height = 23
    +        Top = 15
    +        Width = 436
    +        Align = alTop
    +        ItemHeight = 15
    +        OnChange = DebuggerComboBoxChange
    +        TabOrder = 0
    +        Text = 'DebuggerComboBox'
    +      end
    +      object DebuggerLabel: TLabel
    +        Left = 0
    +        Height = 15
    +        Top = 0
    +        Width = 436
    +        Align = alTop
    +        Caption = 'DebuggerLabel'
    +        ParentColor = False
    +        WordWrap = True
    +      end
    +      object DebuggerBrowseButton: TButton
    +        AnchorSideLeft.Control = FPCSourcesTabSheet
    +        AnchorSideTop.Control = DebuggerComboBox
    +        AnchorSideTop.Side = asrBottom
    +        Left = 6
    +        Height = 25
    +        Top = 38
    +        Width = 152
    +        AutoSize = True
    +        Caption = 'DebuggerBrowseButton'
    +        OnClick = DebuggerBrowseButtonClick
    +        TabOrder = 1
    +      end
    +      object DebuggerMemo: TMemo
    +        AnchorSideTop.Control = DebuggerBrowseButton
    +        AnchorSideTop.Side = asrBottom
    +        Left = 0
    +        Height = 195
    +        Top = 63
    +        Width = 436
    +        Align = alBottom
    +        Anchors = [akTop, akLeft, akRight, akBottom]
    +        Lines.Strings = (
    +          'FPCSrcDirMemo'
    +          ''
    +          ''
    +        )
    +        ReadOnly = True
    +        TabOrder = 2
    +      end
    +    end
       end
       object WelcomePaintBox: TPaintBox
         Left = 0
    Index: ide/initialsetupdlgs.pas
    ===================================================================
    --- ide/initialsetupdlgs.pas	(revision 38091)
    +++ ide/initialsetupdlgs.pas	(working copy)
    @@ -67,7 +67,9 @@
       TSDFilenameType = (
         sddtLazarusSrcDir,
         sddtCompilerFilename,
    -    sddtFPCSrcDir
    +    sddtFPCSrcDir,
    +    sddtMakeExeFilename,
    +    sddtDebuggerFilename
         );
     
       { TInitialSetupDialog }
    @@ -79,9 +81,17 @@
         CompilerLabel: TLabel;
         CompilerMemo: TMemo;
         FPCSrcDirBrowseButton: TButton;
    +    MakeExeBrowseButton: TButton;
    +    DebuggerBrowseButton: TButton;
         FPCSrcDirComboBox: TComboBox;
    +    MakeExeComboBox: TComboBox;
    +    DebuggerComboBox: TComboBox;
         FPCSrcDirLabel: TLabel;
    +    MakeExeLabel: TLabel;
    +    DebuggerLabel: TLabel;
         FPCSrcDirMemo: TMemo;
    +    MakeExeMemo: TMemo;
    +    DebuggerMemo: TMemo;
         ImageList1: TImageList;
         LazDirBrowseButton: TButton;
         LazDirLabel: TLabel;
    @@ -94,15 +104,21 @@
         LazarusTabSheet: TTabSheet;
         CompilerTabSheet: TTabSheet;
         FPCSourcesTabSheet: TTabSheet;
    +    MakeExeTabSheet: TTabSheet;
    +    DebuggerTabSheet: TTabSheet;
         WelcomePaintBox: TPaintBox;
         procedure CompilerBrowseButtonClick(Sender: TObject);
         procedure CompilerComboBoxChange(Sender: TObject);
    +    procedure DebuggerBrowseButtonClick(Sender: TObject);
    +    procedure DebuggerComboBoxChange(Sender: TObject);
         procedure FormCreate(Sender: TObject);
         procedure FormDestroy(Sender: TObject);
         procedure FPCSrcDirBrowseButtonClick(Sender: TObject);
         procedure FPCSrcDirComboBoxChange(Sender: TObject);
         procedure LazDirBrowseButtonClick(Sender: TObject);
         procedure LazDirComboBoxChange(Sender: TObject);
    +    procedure MakeExeBrowseButtonClick(Sender: TObject);
    +    procedure MakeExeComboBoxChange(Sender: TObject);
         procedure PropertiesPageControlChange(Sender: TObject);
         procedure PropertiesTreeViewSelectionChanged(Sender: TObject);
         procedure StartIDEBitBtnClick(Sender: TObject);
    @@ -111,9 +127,13 @@
       private
         FLazarusDirChanged: boolean;
         fCompilerFilenameChanged: boolean;
    +    fMakeExeFilenameChanged: boolean;
    +    fDebuggerFilenameChanged: boolean;
         FLastParsedLazDir: string;
         fLastParsedCompiler: string;
         fLastParsedFPCSrcDir: string;
    +    fLastParsedMakeExe: string;
    +    fLastParsedDebugger: string;
         FIdleConnected: boolean;
         ImgIDError: LongInt;
         ImgIDWarning: LongInt;
    @@ -125,12 +145,16 @@
         procedure UpdateLazarusDirCandidates;
         procedure UpdateCompilerFilenameCandidates;
         procedure UpdateFPCSrcDirCandidates;
    +    procedure UpdateMakeExeCandidates;
    +    procedure UpdateDebuggerCandidates;
         procedure FillComboboxWithFileInfoList(ABox: TComboBox; List: TObjectList;
            ItemIndex: integer = 0);
         procedure SetIdleConnected(const AValue: boolean);
         procedure UpdateLazDirNote;
         procedure UpdateCompilerNote;
         procedure UpdateFPCSrcDirNote;
    +    procedure UpdateMakeExeNote;
    +    procedure UpdateDebuggerNote;
         function FirstErrorNode: TTreeNode;
         function GetFPCVer: string;
         function GetFirstCandidate(Candidates: TObjectList;
    @@ -140,7 +164,9 @@
         TVNodeLazarus: TTreeNode;
         TVNodeCompiler: TTreeNode;
         TVNodeFPCSources: TTreeNode;
    -    procedure Init;
    +    TVNodeMakeExe: TTreeNode;
    +    TVNodeDebugger: TTreeNode;
    +    procedure Init; //Check for config errors, find and show alternatives
         property IdleConnected: boolean read FIdleConnected write SetIdleConnected;
       end;
     
    @@ -164,10 +190,15 @@
     procedure SetupFPCSrcDir(FPCVer: string);
     
     function CheckMakeExeQuality(AFilename: string;
    -  out Note: string): TSDFilenameQuality;
    -function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList;
    -procedure SetupMakeExe;
    +  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid make executable
    +function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList; //Search make candidates and add them to the list, including quality level
    +procedure SetupMakeExe; //Checks if the make specified in user's options (if any) is ok. If not, search for and set a valid one if possible
     
    +function CheckDebuggerQuality(AFilename: string;
    +  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid debugger (only gdb supported for now)
    +function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList; //Search debugger candidates and add them to list, including quality level
    +procedure SetupDebugger; //Checks if the debugger specified in user's option (if any) is ok. If not, search for and set a valid one if possible
    +
     function GetValueFromPrimaryConfig(OptionFilename, Path: string): string;
     function GetValueFromSecondaryConfig(OptionFilename, Path: string): string;
     function GetValueFromIDEConfig(OptionFilename, Path: string): string;
    @@ -565,7 +596,7 @@
     
         // check $(LazarusDir)\fpc\bin\i386-win32\fpc.exe
         if CheckFile(SetDirSeparators('$(LazarusDir)/fpc/bin/$(TargetCPU)-$(TargetOS)/')+ShortCompFile,Result)
    -    then exit;
    +      then exit;
     
         // check common directories
         Files:=TStringList.Create;
    @@ -577,8 +608,8 @@
           Files.Free;
         end;
     
    +    // Windows-only locations:
         if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
    -      // Windows has some special places
           SysDrive:=GetEnvironmentVariableUTF8('SYSTEMDRIVE');
           if SysDrive='' then SysDrive:='C:';
           SysDrive:=AppendPathDelim(SysDrive);
    @@ -842,6 +873,165 @@
       end;
     end;
     
    +function CheckDebuggerQuality(AFilename: string; out Note: string
    +  ): TSDFilenameQuality;
    +begin
    +  Result:=sddqInvalid;
    +  AFilename:=TrimFilename(AFilename);
    +  if not FileExistsCached(AFilename) then
    +  begin
    +    Note:=lisFileNotFound4;
    +    exit;
    +  end;
    +  if DirPathExistsCached(AFilename) then
    +  begin
    +    Note:=lisFileIsDirectory;
    +    exit;
    +  end;
    +  if not FileIsExecutableCached(AFilename) then
    +  begin
    +    Note:=lisFileIsNotAnExecutable;
    +    exit;
    +  end;
    +
    +  { We could call gdb and parse the output looking for something like
    +  GNU gdb, but that may be going too far. }
    +  Note:=lisOk;
    +  Result:=sddqCompatible;
    +end;
    +
    +function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList;
    +
    +  function CheckFile(AFilename: string; var List: TObjectList): boolean;
    +  var
    +    Item: TSDFileInfo;
    +    RealFilename: String;
    +  begin
    +    Result:=false;
    +    if AFilename='' then exit;
    +    DoDirSeparators(AFilename);
    +    // check if already checked
    +    if CaptionInSDFileList(AFilename,List) then exit;
    +    EnvironmentOptions.DebuggerFilename:=AFilename;
    +    RealFilename:=EnvironmentOptions.GetParsedDebuggerFilename;
    +    debugln(['SearchDebuggerCandidates Value=',AFilename,' File=',RealFilename]);
    +    if RealFilename='' then exit;
    +    // check if exists
    +    if not FileExistsCached(RealFilename) then exit;
    +    // add to list and check quality
    +    Item:=TSDFileInfo.Create;
    +    Item.Filename:=RealFilename;
    +    Item.Quality:=CheckDebuggerQuality(RealFilename,Item.Note);
    +    Item.Caption:=AFilename;
    +    if List=nil then
    +      List:=TObjectList.create(true);
    +    List.Add(Item);
    +    Result:=(Item.Quality=sddqCompatible) and StopIfFits;
    +  end;
    +const
    +  DebuggerFileName='gdb'; //For Windows, .exe will be appended
    +var
    +  OldDebuggerFilename: String;
    +  AFilename: String;
    +  Files: TStringList;
    +  i: Integer;
    +begin
    +  Result:=nil;
    +
    +  OldDebuggerFilename:=EnvironmentOptions.DebuggerFilename;
    +  try
    +    // check current setting
    +    if CheckFile(EnvironmentOptions.DebuggerFilename,Result) then exit;
    +
    +    // check the primary options
    +    AFilename:=GetValueFromPrimaryConfig(EnvOptsConfFileName,
    +                                    'EnvironmentOptions/DebuggerFilename/Value');
    +    if CheckFile(AFilename,Result) then exit;
    +
    +    // check the secondary options
    +    AFilename:=GetValueFromSecondaryConfig(EnvOptsConfFileName,
    +                                    'EnvironmentOptions/DebuggerFilename/Value');
    +    if CheckFile(AFilename,Result) then exit;
    +
    +    // The next 2 locations are locations used by older and newer versions of the Windows installers
    +    // If other platform installers follow the same strategy, this can be useful.
    +    // Chances of this are low (gdb is generally installed in the path on Unixy systems), but it can't hurt...
    +    // and it can be useful for cross compiling/custom setups.
    +
    +    // Check new installation location: $(LazarusDir)\mingw\$(TargetCPU)-$(TargetOS)\bin\gdb.exe
    +    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/$(TargetCPU)-$(TargetOS)/bin/'+DebuggerFileName+GetExecutableExt),Result)
    +      then exit;
    +
    +    // Older Lazarus installers did not use macros for their debuggers: there was only one debugger
    +    // Check old installation location: $(LazarusDir)\mingw\bin\gdb.exe
    +    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/bin/'+DebuggerFileName+GetExecutableExt),Result)
    +      then exit;
    +
    +    // Windows-only locations:
    +    if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
    +      // check for debugger in fpc.exe directory - could be a lucky shot
    +      if CheckFile(SetDirSeparators('$Path($(CompPath))/'+DebuggerFileName+GetExecutableExt),Result)
    +        then exit;
    +    end;
    +
    +    // check history
    +    Files:=EnvironmentOptions.DebuggerFileHistory;
    +    if Files<>nil then
    +      for i:=0 to Files.Count-1 do
    +        if CheckFile(Files[i],Result) then exit;
    +
    +    // check PATH
    +    AFilename:=DebuggerFileName;
    +    AFilename+=GetExecutableExt;
    +    if CheckFile(FindDefaultExecutablePath(AFilename),Result) then exit;
    +
    +    // There are no common directories apart from the PATH
    +    // where gdb would be installed. Otherwise we could do something similar as
    +    // in SearchMakeExeCandidates.
    +  finally
    +    EnvironmentOptions.DebuggerFilename:=OldDebuggerFilename;
    +  end;
    +end;
    +
    +procedure SetupDebugger;
    +var
    +  Note: string;
    +  Filename: String;
    +  Quality: TSDFilenameQuality;
    +  BestDir: TSDFileInfo;
    +  List: TObjectList;
    +begin
    +  Filename:=EnvironmentOptions.GetParsedDebuggerFilename;
    +  Quality:=CheckDebuggerQuality(Filename,Note);
    +  if Quality<>sddqInvalid then exit;
    +  // bad debugger
    +  dbgout('SetupDebugger:');
    +  if EnvironmentOptions.DebuggerFilename<>'' then
    +  begin
    +    dbgout(' The "gdb" executable "',EnvironmentOptions.DebuggerFilename,'"');
    +    if EnvironmentOptions.DebuggerFilename<>Filename then
    +      dbgout(' => "',Filename,'"');
    +    dbgout(' is invalid (Error: ',Note,')');
    +    debugln(' Searching a proper one ...');
    +  end else begin
    +    debugln(' Searching "gdb" ...');
    +  end;
    +  List:=SearchDebuggerCandidates(true);
    +  try
    +    BestDir:=nil;
    +    if List<>nil then
    +      BestDir:=TSDFileInfo(List[List.Count-1]);
    +    if (BestDir=nil) or (BestDir.Quality=sddqInvalid) then begin
    +      debugln(['SetupDebugger: no proper "gdb" found.']);
    +      exit;
    +    end;
    +    EnvironmentOptions.DebuggerFilename:=BestDir.Filename;
    +    debugln(['SetupDebugger: using ',EnvironmentOptions.DebuggerFilename]);
    +  finally
    +    List.Free;
    +  end;
    +end;
    +
     function CheckMakeExeQuality(AFilename: string; out Note: string
       ): TSDFilenameQuality;
     begin
    @@ -863,11 +1053,13 @@
         exit;
       end;
     
    +  // Windows-only locations:
       if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
    -    // under Windows the make.exe is in the same directory as fpc.exe
    +    // under Windows, make.exe is in the same directory as fpc.exe
         if not FileExistsCached(ExtractFilePath(AFilename)+'fpc.exe') then begin
    -      Note:='There is no fpc.exe in the directory of the '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the fpc compiler.';
    +      Note:='There is no fpc.exe in the directory of '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the FPC compiler.';
           Result:=sddqIncomplete;
    +      exit;
         end;
       end;
     
    @@ -926,6 +1118,7 @@
                                         'EnvironmentOptions/MakeFilename/Value');
         if CheckFile(AFilename,Result) then exit;
     
    +    // Windows-only locations:
         if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
           // check make in fpc.exe directory
           if CheckFile(SetDirSeparators('$Path($(CompPath))/make.exe'),Result)
    @@ -1098,6 +1291,8 @@
       LazarusTabSheet.Caption:='Lazarus';
       CompilerTabSheet.Caption:=lisCompiler;
       FPCSourcesTabSheet.Caption:=lisFPCSources;
    +  MakeExeTabSheet.Caption:='make';
    +  DebuggerTabSheet.Caption:=lisDebugger;
     
       FHeadGraphic:=TPortableNetworkGraphic.Create;
       FHeadGraphic.LoadFromLazarusResource('ide_icon48x48');
    @@ -1105,6 +1300,8 @@
       TVNodeLazarus:=PropertiesTreeView.Items.Add(nil,LazarusTabSheet.Caption);
       TVNodeCompiler:=PropertiesTreeView.Items.Add(nil,CompilerTabSheet.Caption);
       TVNodeFPCSources:=PropertiesTreeView.Items.Add(nil,FPCSourcesTabSheet.Caption);
    +  TVNodeMakeExe:=PropertiesTreeView.Items.Add(nil,MakeExeTabSheet.Caption);
    +  TVNodeDebugger:=PropertiesTreeView.Items.Add(nil,DebuggerTabSheet.Caption);
       ImgIDError := ImageList1.AddLazarusResource('state_error');
       ImgIDWarning := ImageList1.AddLazarusResource('state_warning');
     
    @@ -1122,6 +1319,15 @@
       FPCSrcDirLabel.Caption:=Format(
         lisTheSourcesOfTheFreePascalPackagesAreRequiredForBro, [SetDirSeparators('rtl'
         +'/linux/system.pp')]);
    +
    +  MakeExeBrowseButton.Caption:=lisPathEditBrowse;
    +  MakeExeLabel.Caption:=Format(
    +    lisTheMakeExecutableTypicallyHasTheName, ['make'+GetExecutableExt('')]);
    +
    +  DebuggerBrowseButton.Caption:=lisPathEditBrowse;
    +  DebuggerLabel.Caption:=Format(
    +    lisTheDebuggerExecutableTypicallyHasTheName, ['gdb'+GetExecutableExt('')]);
    +
     end;
     
     procedure TInitialSetupDialog.CompilerComboBoxChange(Sender: TObject);
    @@ -1129,6 +1335,35 @@
       UpdateCompilerNote;
     end;
     
    +procedure TInitialSetupDialog.DebuggerBrowseButtonClick(Sender: TObject);
    +var
    +  Filename: String;
    +  Dlg: TOpenDialog;
    +  Filter: String;
    +begin
    +  Dlg:=TOpenDialog.Create(nil);
    +  try
    +    Filename:='gdb'+GetExecutableExt;
    +    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
    +    Dlg.Options:=Dlg.Options+[ofFileMustExist];
    +    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
    +    if ExtractFileExt(Filename)<>'' then
    +      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
    +    Dlg.Filter:=Filter;
    +    if not Dlg.Execute then exit;
    +    Filename:=Dlg.FileName;
    +  finally
    +    Dlg.Free;
    +  end;
    +  DebuggerComboBox.Text:=Filename;
    +  UpdateDebuggerNote;
    +end;
    +
    +procedure TInitialSetupDialog.DebuggerComboBoxChange(Sender: TObject);
    +begin
    +  UpdateDebuggerNote;
    +end;
    +
     procedure TInitialSetupDialog.CompilerBrowseButtonClick(Sender: TObject);
     var
       Filename: String;
    @@ -1193,6 +1428,35 @@
       UpdateLazDirNote;
     end;
     
    +procedure TInitialSetupDialog.MakeExeBrowseButtonClick(Sender: TObject);
    +var
    +  Filename: String;
    +  Dlg: TOpenDialog;
    +  Filter: String;
    +begin
    +  Dlg:=TOpenDialog.Create(nil);
    +  try
    +    Filename:='make'+GetExecutableExt;
    +    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
    +    Dlg.Options:=Dlg.Options+[ofFileMustExist];
    +    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
    +    if ExtractFileExt(Filename)<>'' then
    +      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
    +    Dlg.Filter:=Filter;
    +    if not Dlg.Execute then exit;
    +    Filename:=Dlg.FileName;
    +  finally
    +    Dlg.Free;
    +  end;
    +  MakeExeComboBox.Text:=Filename;
    +  UpdateMakeExeNote;
    +end;
    +
    +procedure TInitialSetupDialog.MakeExeComboBoxChange(Sender: TObject);
    +begin
    +  UpdateMakeExeNote;
    +end;
    +
     procedure TInitialSetupDialog.PropertiesPageControlChange(Sender: TObject);
     var
       s: String;
    @@ -1225,7 +1489,11 @@
       else if Node=TVNodeCompiler then
         s:=lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW
       else if Node=TVNodeFPCSources then
    -    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio;
    +    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio
    +  else if Node=TVNodeMakeExe then
    +    s:=lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp
    +  else if Node=TVNodeDebugger then
    +    s:=lisWithoutAProperDebuggerDebuggingWillBeDisappointing;
       if s<>'' then begin
         MsgResult:=MessageDlg(lisCCOWarningCaption, s, mtWarning, [mbIgnore,
           mbCancel], 0);
    @@ -1241,9 +1509,13 @@
       s:=FPCSrcDirComboBox.Text;
       if s<>'' then
         EnvironmentOptions.FPCSourceDirectory:=s;
    +  s:=MakeExeComboBox.Text;
    +  if s<>'' then
    +    EnvironmentOptions.MakeFilename:=s;
    +  s:=DebuggerComboBox.Text;
    +  if s<>'' then
    +    EnvironmentOptions.DebuggerFilename:=s;
     
    -  SetupMakeExe;
    -
       ModalResult:=mrOk;
     end;
     
    @@ -1267,6 +1539,12 @@
       end else if fCompilerFilenameChanged then begin
         UpdateFPCSrcDirCandidates;
         UpdateFPCSrcDirNote;
    +  end else if fMakeExeFilenameChanged then begin
    +    UpdateMakeExeCandidates;
    +    UpdateMakeExeNote;
    +  end else if fDebuggerFilenameChanged then begin
    +    UpdateDebuggerCandidates;
    +    UpdateDebuggerNote;
       end else
         IdleConnected:=false;
     end;
    @@ -1341,6 +1619,28 @@
       FillComboboxWithFileInfoList(FPCSrcDirComboBox,Dirs);
     end;
     
    +procedure TInitialSetupDialog.UpdateMakeExeCandidates;
    +var
    +  Files: TObjectList;
    +begin
    +  FLazarusDirChanged:=false;
    +  Files:=SearchMakeExeCandidates(false);
    +  FreeAndNil(FCandidates[sddtMakeExeFileName]);
    +  FCandidates[sddtMakeExeFileName]:=Files;
    +  FillComboboxWithFileInfoList(MakeExeComboBox,Files);
    +end;
    +
    +procedure TInitialSetupDialog.UpdateDebuggerCandidates;
    +var
    +  Files: TObjectList;
    +begin
    +  FLazarusDirChanged:=false;
    +  Files:=SearchDebuggerCandidates(false);
    +  FreeAndNil(FCandidates[sddtDebuggerFilename]);
    +  FCandidates[sddtDebuggerFilename]:=Files;
    +  FillComboboxWithFileInfoList(DebuggerComboBox,Files);
    +end;
    +
     procedure TInitialSetupDialog.FillComboboxWithFileInfoList(ABox: TComboBox;
       List: TObjectList; ItemIndex: integer);
     var
    @@ -1479,6 +1779,76 @@
       TVNodeFPCSources.SelectedIndex:=ImageIndex;
     end;
     
    +procedure TInitialSetupDialog.UpdateMakeExeNote;
    +var
    +  CurCaption: String;
    +  Note: string;
    +  Quality: TSDFilenameQuality;
    +  s: String;
    +  ImageIndex: Integer;
    +begin
    +  if csDestroying in ComponentState then exit;
    +  CurCaption:=MakeExeComboBox.Text;
    +  EnvironmentOptions.MakeFilename:=CurCaption;
    +  if fLastParsedMakeExe=EnvironmentOptions.GetParsedMakeFilename then exit;
    +  fLastParsedMakeExe:=EnvironmentOptions.GetParsedMakeFilename;
    +  //debugln(['TInitialSetupDialog.UpdateMakeExeNote ',fLastParsedMakeExe]);
    +  Quality:=CheckMakeExeQuality(fLastParsedMakeExe,Note);
    +
    +  case Quality of
    +  sddqInvalid: s:=lisError;
    +  sddqCompatible: s:='';
    +  else s:=lisWarning;
    +  end;
    +  if EnvironmentOptions.MakeFilename<>EnvironmentOptions.GetParsedMakeFilename
    +  then
    +    s:=lisFile2+EnvironmentOptions.GetParsedMakeFilename+LineEnding+
    +      LineEnding+s;
    +  MakeExeMemo.Text:=s+Note;
    +
    +  ImageIndex:=QualityToImgIndex(Quality);
    +  TVNodeMakeExe.ImageIndex:=ImageIndex;
    +  TVNodeMakeExe.SelectedIndex:=ImageIndex;
    +
    +  fMakeExeFilenameChanged:=true;
    +  IdleConnected:=true;
    +end;
    +
    +procedure TInitialSetupDialog.UpdateDebuggerNote;
    +var
    +  CurCaption: String;
    +  Note: string;
    +  Quality: TSDFilenameQuality;
    +  s: String;
    +  ImageIndex: Integer;
    +begin
    +  if csDestroying in ComponentState then exit;
    +  CurCaption:=DebuggerComboBox.Text;
    +  EnvironmentOptions.DebuggerFilename:=CurCaption;
    +  if fLastParsedDebugger=EnvironmentOptions.GetParsedDebuggerFilename then exit;
    +  fLastParsedDebugger:=EnvironmentOptions.GetParsedDebuggerFilename;
    +  //debugln(['TInitialSetupDialog.UpdateDebuggerNote ',fLastParsedDebugger]);
    +  Quality:=CheckDebuggerQuality(fLastParsedDebugger,Note);
    +
    +  case Quality of
    +  sddqInvalid: s:=lisError;
    +  sddqCompatible: s:='';
    +  else s:=lisWarning;
    +  end;
    +  if EnvironmentOptions.DebuggerFilename<>EnvironmentOptions.GetParsedDebuggerFilename
    +  then
    +    s:=lisFile2+EnvironmentOptions.GetParsedDebuggerFilename+LineEnding+
    +      LineEnding+s;
    +  DebuggerMemo.Text:=s+Note;
    +
    +  ImageIndex:=QualityToImgIndex(Quality);
    +  TVNodeDebugger.ImageIndex:=ImageIndex;
    +  TVNodeDebugger.SelectedIndex:=ImageIndex;
    +
    +  fDebuggerFilenameChanged:=true;
    +  IdleConnected:=true;
    +end;
    +
     function TInitialSetupDialog.FirstErrorNode: TTreeNode;
     var
       i: Integer;
    @@ -1518,6 +1888,8 @@
         Result:=-1
       else if Quality=sddqWrongMinorVersion then
         Result:=ImgIDWarning
    +  else if Quality=sddqIncomplete then
    +    Result:=ImgIDWarning
       else
         Result:=ImgIDError;
     end;
    @@ -1568,6 +1940,32 @@
       fLastParsedFPCSrcDir:='. .';
       UpdateFPCSrcDirNote;
     
    +  // Make executable
    +  UpdateMakeExeCandidates;
    +  if (not FileExistsCached(EnvironmentOptions.Filename)) then
    +  begin
    +    // first start => choose first best candidate
    +    Candidate:=GetFirstCandidate(FCandidates[sddtMakeExeFilename]);
    +    if Candidate<>nil then
    +      EnvironmentOptions.MakeFilename:=Candidate.Caption;
    +  end;
    +  MakeExeComboBox.Text:=EnvironmentOptions.MakeFilename;
    +  fLastParsedMakeExe:='. .';
    +  UpdateMakeExeNote;
    +
    +  // Debugger
    +  UpdateDebuggerCandidates;
    +  if (not FileExistsCached(EnvironmentOptions.Filename)) then
    +  begin
    +    // first start => choose first best candidate
    +    Candidate:=GetFirstCandidate(FCandidates[sddtDebuggerFilename]);
    +    if Candidate<>nil then
    +      EnvironmentOptions.DebuggerFilename:=Candidate.Caption;
    +  end;
    +  DebuggerComboBox.Text:=EnvironmentOptions.DebuggerFilename;
    +  fLastParsedDebugger:='. .';
    +  UpdateDebuggerNote;
    +
       // select first error
       Node:=FirstErrorNode;
       if Node=nil then
    Index: tools/install/win/environmentoptions.xml
    ===================================================================
    --- tools/install/win/environmentoptions.xml	(revision 38091)
    +++ tools/install/win/environmentoptions.xml	(working copy)
    @@ -13,7 +13,7 @@
         <TestBuildDirectory Value="%Temp%">
         </TestBuildDirectory>
         <Debugger Class="TGDBMIDebugger"/>
    -    <DebuggerFilename Value="%LazDir%\mingw\bin\gdb.exe">
    +    <DebuggerFilename Value="%LazDir%\mingw\$(TargetCPU)-$(TargetOS)\bin\gdb.exe">
         </DebuggerFilename>
       </EnvironmentOptions>
     </CONFIG>
    
  • initial_checkdebugger2.diff (33,660 bytes)
    Index: ide/initialsetupdlgs.lfm
    ===================================================================
    --- ide/initialsetupdlgs.lfm	(revision 38091)
    +++ ide/initialsetupdlgs.lfm	(working copy)
    @@ -1,8 +1,8 @@
     object InitialSetupDialog: TInitialSetupDialog
       AnchorSideBottom.Side = asrBottom
    -  Left = 253
    +  Left = 319
       Height = 385
    -  Top = 253
    +  Top = 238
       Width = 620
       Caption = 'InitialSetupDialog'
       ClientHeight = 385
    @@ -10,7 +10,7 @@
       OnCreate = FormCreate
       OnDestroy = FormDestroy
       Position = poScreenCenter
    -  LCLVersion = '0.9.31'
    +  LCLVersion = '1.1'
       object PropertiesTreeView: TTreeView
         AnchorSideLeft.Control = Owner
         AnchorSideTop.Control = WelcomePaintBox
    @@ -18,7 +18,7 @@
         AnchorSideRight.Control = Splitter1
         AnchorSideBottom.Control = BtnPanel
         Left = 6
    -    Height = 289
    +    Height = 286
         Top = 54
         Width = 159
         Anchors = [akTop, akLeft, akRight, akBottom]
    @@ -40,7 +40,7 @@
         AnchorSideBottom.Control = PropertiesTreeView
         AnchorSideBottom.Side = asrBottom
         Left = 165
    -    Height = 289
    +    Height = 286
         Top = 54
         Width = 5
         Align = alNone
    @@ -48,21 +48,21 @@
       end
       object BtnPanel: TPanel
         Left = 10
    -    Height = 22
    -    Top = 353
    +    Height = 25
    +    Top = 350
         Width = 600
         Align = alBottom
         AutoSize = True
         BorderSpacing.Around = 10
         BevelOuter = bvNone
    -    ClientHeight = 22
    +    ClientHeight = 25
         ClientWidth = 600
         TabOrder = 2
         object StartIDEBitBtn: TBitBtn
    -      Left = 489
    -      Height = 22
    +      Left = 500
    +      Height = 25
           Top = 0
    -      Width = 111
    +      Width = 100
           Align = alRight
           AutoSize = True
           Caption = 'StartIDEBitBtn'
    @@ -80,13 +80,13 @@
         AnchorSideBottom.Control = Splitter1
         AnchorSideBottom.Side = asrBottom
         Left = 170
    -    Height = 289
    +    Height = 286
         Top = 54
         Width = 444
    -    ActivePage = FPCSourcesTabSheet
    +    ActivePage = LazarusTabSheet
         Anchors = [akTop, akLeft, akRight, akBottom]
         BorderSpacing.Right = 6
    -    TabIndex = 2
    +    TabIndex = 0
         TabOrder = 3
         OnChange = PropertiesPageControlChange
         Options = [nboHidePageListPopup]
    @@ -96,11 +96,11 @@
           ChildSizing.TopBottomSpacing = 6
           ChildSizing.HorizontalSpacing = 6
           ChildSizing.VerticalSpacing = 6
    -      ClientHeight = 255
    -      ClientWidth = 442
    +      ClientHeight = 258
    +      ClientWidth = 436
           object LazDirLabel: TLabel
             Left = 6
    -        Height = 14
    +        Height = 15
             Top = 6
             Width = 424
             Align = alTop
    @@ -115,11 +115,11 @@
             AnchorSideRight.Control = LazarusTabSheet
             AnchorSideRight.Side = asrBottom
             Left = 6
    -        Height = 21
    -        Top = 26
    +        Height = 23
    +        Top = 27
             Width = 424
             Anchors = [akTop, akLeft, akRight]
    -        ItemHeight = 0
    +        ItemHeight = 15
             OnChange = LazDirComboBoxChange
             TabOrder = 0
             Text = 'LazDirComboBox'
    @@ -128,8 +128,8 @@
             AnchorSideTop.Control = LazDirBrowseButton
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 174
    -        Top = 82
    +        Height = 165
    +        Top = 87
             Width = 424
             Align = alBottom
             Anchors = [akTop, akLeft, akRight, akBottom]
    @@ -148,9 +148,9 @@
             AnchorSideTop.Side = asrBottom
             AnchorSideRight.Side = asrBottom
             Left = 6
    -        Height = 23
    -        Top = 53
    -        Width = 122
    +        Height = 25
    +        Top = 56
    +        Width = 132
             AutoSize = True
             Caption = 'LazDirBrowseButton'
             OnClick = LazDirBrowseButtonClick
    @@ -163,13 +163,13 @@
           ChildSizing.TopBottomSpacing = 6
           ChildSizing.HorizontalSpacing = 6
           ChildSizing.VerticalSpacing = 6
    -      ClientHeight = 250
    -      ClientWidth = 438
    +      ClientHeight = 258
    +      ClientWidth = 436
           object CompilerLabel: TLabel
             Left = 6
    -        Height = 17
    +        Height = 15
             Top = 6
    -        Width = 426
    +        Width = 424
             Align = alTop
             Caption = 'CompilerLabel'
             ParentColor = False
    @@ -182,11 +182,11 @@
             AnchorSideRight.Control = CompilerTabSheet
             AnchorSideRight.Side = asrBottom
             Left = 6
    -        Height = 21
    -        Top = 29
    -        Width = 426
    +        Height = 23
    +        Top = 27
    +        Width = 424
             Anchors = [akTop, akLeft, akRight]
    -        ItemHeight = 0
    +        ItemHeight = 15
             OnChange = CompilerComboBoxChange
             TabOrder = 0
             Text = 'CompilerComboBox'
    @@ -196,9 +196,9 @@
             AnchorSideTop.Control = CompilerComboBox
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 20
    +        Height = 25
             Top = 56
    -        Width = 168
    +        Width = 149
             AutoSize = True
             Caption = 'CompilerBrowseButton'
             OnClick = CompilerBrowseButtonClick
    @@ -213,9 +213,9 @@
             AnchorSideBottom.Control = CompilerTabSheet
             AnchorSideBottom.Side = asrBottom
             Left = 6
    -        Height = 162
    -        Top = 82
    -        Width = 426
    +        Height = 165
    +        Top = 87
    +        Width = 424
             Anchors = [akTop, akLeft, akRight, akBottom]
             Lines.Strings = (
               'CompilerMemo'
    @@ -232,13 +232,13 @@
           ChildSizing.TopBottomSpacing = 6
           ChildSizing.HorizontalSpacing = 6
           ChildSizing.VerticalSpacing = 6
    -      ClientHeight = 250
    -      ClientWidth = 438
    +      ClientHeight = 258
    +      ClientWidth = 436
           object FPCSrcDirLabel: TLabel
             Left = 6
    -        Height = 17
    +        Height = 15
             Top = 6
    -        Width = 426
    +        Width = 424
             Align = alTop
             Caption = 'FPCSrcDirLabel'
             ParentColor = False
    @@ -246,11 +246,11 @@
           end
           object FPCSrcDirComboBox: TComboBox
             Left = 6
    -        Height = 21
    -        Top = 29
    -        Width = 426
    +        Height = 23
    +        Top = 27
    +        Width = 424
             Align = alTop
    -        ItemHeight = 0
    +        ItemHeight = 15
             OnChange = FPCSrcDirComboBoxChange
             TabOrder = 0
             Text = 'FPCSrcDirComboBox'
    @@ -260,9 +260,9 @@
             AnchorSideTop.Control = FPCSrcDirComboBox
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 20
    +        Height = 25
             Top = 56
    -        Width = 171
    +        Width = 152
             AutoSize = True
             Caption = 'FPCSrcDirBrowseButton'
             OnClick = FPCSrcDirBrowseButtonClick
    @@ -272,9 +272,9 @@
             AnchorSideTop.Control = FPCSrcDirBrowseButton
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 162
    -        Top = 82
    -        Width = 426
    +        Height = 165
    +        Top = 87
    +        Width = 424
             Align = alBottom
             Anchors = [akTop, akLeft, akRight, akBottom]
             Lines.Strings = (
    @@ -286,6 +286,118 @@
             TabOrder = 2
           end
         end
    +    object MakeExeTabSheet: TTabSheet
    +      Caption = 'MakeExeTabSheet'
    +      ClientHeight = 258
    +      ClientWidth = 436
    +      object MakeExeComboBox: TComboBox
    +        Left = 0
    +        Height = 23
    +        Top = 15
    +        Width = 436
    +        Align = alTop
    +        ItemHeight = 15
    +        OnChange = MakeExeComboBoxChange
    +        TabOrder = 0
    +        Text = 'MakeExeComboBox'
    +      end
    +      object MakeExeLabel: TLabel
    +        Left = 0
    +        Height = 15
    +        Top = 0
    +        Width = 436
    +        Align = alTop
    +        Caption = 'MakeExeLabel'
    +        ParentColor = False
    +        WordWrap = True
    +      end
    +      object MakeExeBrowseButton: TButton
    +        AnchorSideLeft.Control = FPCSourcesTabSheet
    +        AnchorSideTop.Control = MakeExeComboBox
    +        AnchorSideTop.Side = asrBottom
    +        Left = 6
    +        Height = 25
    +        Top = 38
    +        Width = 146
    +        AutoSize = True
    +        Caption = 'MakeExeBrowseButton'
    +        OnClick = MakeExeBrowseButtonClick
    +        TabOrder = 1
    +      end
    +      object MakeExeMemo: TMemo
    +        AnchorSideTop.Control = MakeExeBrowseButton
    +        AnchorSideTop.Side = asrBottom
    +        Left = 0
    +        Height = 195
    +        Top = 63
    +        Width = 436
    +        Align = alBottom
    +        Anchors = [akTop, akLeft, akRight, akBottom]
    +        Lines.Strings = (
    +          'FPCSrcDirMemo'
    +          ''
    +          ''
    +        )
    +        ReadOnly = True
    +        TabOrder = 2
    +      end
    +    end
    +    object DebuggerTabSheet: TTabSheet
    +      Caption = 'DebuggerTabSheet'
    +      ClientHeight = 258
    +      ClientWidth = 436
    +      object DebuggerComboBox: TComboBox
    +        Left = 0
    +        Height = 23
    +        Top = 15
    +        Width = 436
    +        Align = alTop
    +        ItemHeight = 15
    +        OnChange = DebuggerComboBoxChange
    +        TabOrder = 0
    +        Text = 'DebuggerComboBox'
    +      end
    +      object DebuggerLabel: TLabel
    +        Left = 0
    +        Height = 15
    +        Top = 0
    +        Width = 436
    +        Align = alTop
    +        Caption = 'DebuggerLabel'
    +        ParentColor = False
    +        WordWrap = True
    +      end
    +      object DebuggerBrowseButton: TButton
    +        AnchorSideLeft.Control = FPCSourcesTabSheet
    +        AnchorSideTop.Control = DebuggerComboBox
    +        AnchorSideTop.Side = asrBottom
    +        Left = 6
    +        Height = 25
    +        Top = 38
    +        Width = 152
    +        AutoSize = True
    +        Caption = 'DebuggerBrowseButton'
    +        OnClick = DebuggerBrowseButtonClick
    +        TabOrder = 1
    +      end
    +      object DebuggerMemo: TMemo
    +        AnchorSideTop.Control = DebuggerBrowseButton
    +        AnchorSideTop.Side = asrBottom
    +        Left = 0
    +        Height = 195
    +        Top = 63
    +        Width = 436
    +        Align = alBottom
    +        Anchors = [akTop, akLeft, akRight, akBottom]
    +        Lines.Strings = (
    +          'FPCSrcDirMemo'
    +          ''
    +          ''
    +        )
    +        ReadOnly = True
    +        TabOrder = 2
    +      end
    +    end
       end
       object WelcomePaintBox: TPaintBox
         Left = 0
    Index: ide/initialsetupdlgs.pas
    ===================================================================
    --- ide/initialsetupdlgs.pas	(revision 38091)
    +++ ide/initialsetupdlgs.pas	(working copy)
    @@ -67,7 +67,9 @@
       TSDFilenameType = (
         sddtLazarusSrcDir,
         sddtCompilerFilename,
    -    sddtFPCSrcDir
    +    sddtFPCSrcDir,
    +    sddtMakeExeFilename,
    +    sddtDebuggerFilename
         );
     
       { TInitialSetupDialog }
    @@ -79,9 +81,17 @@
         CompilerLabel: TLabel;
         CompilerMemo: TMemo;
         FPCSrcDirBrowseButton: TButton;
    +    MakeExeBrowseButton: TButton;
    +    DebuggerBrowseButton: TButton;
         FPCSrcDirComboBox: TComboBox;
    +    MakeExeComboBox: TComboBox;
    +    DebuggerComboBox: TComboBox;
         FPCSrcDirLabel: TLabel;
    +    MakeExeLabel: TLabel;
    +    DebuggerLabel: TLabel;
         FPCSrcDirMemo: TMemo;
    +    MakeExeMemo: TMemo;
    +    DebuggerMemo: TMemo;
         ImageList1: TImageList;
         LazDirBrowseButton: TButton;
         LazDirLabel: TLabel;
    @@ -94,15 +104,21 @@
         LazarusTabSheet: TTabSheet;
         CompilerTabSheet: TTabSheet;
         FPCSourcesTabSheet: TTabSheet;
    +    MakeExeTabSheet: TTabSheet;
    +    DebuggerTabSheet: TTabSheet;
         WelcomePaintBox: TPaintBox;
         procedure CompilerBrowseButtonClick(Sender: TObject);
         procedure CompilerComboBoxChange(Sender: TObject);
    +    procedure DebuggerBrowseButtonClick(Sender: TObject);
    +    procedure DebuggerComboBoxChange(Sender: TObject);
         procedure FormCreate(Sender: TObject);
         procedure FormDestroy(Sender: TObject);
         procedure FPCSrcDirBrowseButtonClick(Sender: TObject);
         procedure FPCSrcDirComboBoxChange(Sender: TObject);
         procedure LazDirBrowseButtonClick(Sender: TObject);
         procedure LazDirComboBoxChange(Sender: TObject);
    +    procedure MakeExeBrowseButtonClick(Sender: TObject);
    +    procedure MakeExeComboBoxChange(Sender: TObject);
         procedure PropertiesPageControlChange(Sender: TObject);
         procedure PropertiesTreeViewSelectionChanged(Sender: TObject);
         procedure StartIDEBitBtnClick(Sender: TObject);
    @@ -111,9 +127,13 @@
       private
         FLazarusDirChanged: boolean;
         fCompilerFilenameChanged: boolean;
    +    fMakeExeFilenameChanged: boolean;
    +    fDebuggerFilenameChanged: boolean;
         FLastParsedLazDir: string;
         fLastParsedCompiler: string;
         fLastParsedFPCSrcDir: string;
    +    fLastParsedMakeExe: string;
    +    fLastParsedDebugger: string;
         FIdleConnected: boolean;
         ImgIDError: LongInt;
         ImgIDWarning: LongInt;
    @@ -125,12 +145,16 @@
         procedure UpdateLazarusDirCandidates;
         procedure UpdateCompilerFilenameCandidates;
         procedure UpdateFPCSrcDirCandidates;
    +    procedure UpdateMakeExeCandidates;
    +    procedure UpdateDebuggerCandidates;
         procedure FillComboboxWithFileInfoList(ABox: TComboBox; List: TObjectList;
            ItemIndex: integer = 0);
         procedure SetIdleConnected(const AValue: boolean);
         procedure UpdateLazDirNote;
         procedure UpdateCompilerNote;
         procedure UpdateFPCSrcDirNote;
    +    procedure UpdateMakeExeNote;
    +    procedure UpdateDebuggerNote;
         function FirstErrorNode: TTreeNode;
         function GetFPCVer: string;
         function GetFirstCandidate(Candidates: TObjectList;
    @@ -140,7 +164,9 @@
         TVNodeLazarus: TTreeNode;
         TVNodeCompiler: TTreeNode;
         TVNodeFPCSources: TTreeNode;
    -    procedure Init;
    +    TVNodeMakeExe: TTreeNode;
    +    TVNodeDebugger: TTreeNode;
    +    procedure Init; //Check for config errors, find and show alternatives
         property IdleConnected: boolean read FIdleConnected write SetIdleConnected;
       end;
     
    @@ -164,10 +190,15 @@
     procedure SetupFPCSrcDir(FPCVer: string);
     
     function CheckMakeExeQuality(AFilename: string;
    -  out Note: string): TSDFilenameQuality;
    -function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList;
    -procedure SetupMakeExe;
    +  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid make executable
    +function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList; //Search make candidates and add them to the list, including quality level
    +procedure SetupMakeExe; //Checks if the make specified in user's options (if any) is ok. If not, search for and set a valid one if possible
     
    +function CheckDebuggerQuality(AFilename: string;
    +  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid debugger (only gdb supported for now)
    +function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList; //Search debugger candidates and add them to list, including quality level
    +procedure SetupDebugger; //Checks if the debugger specified in user's option (if any) is ok. If not, search for and set a valid one if possible
    +
     function GetValueFromPrimaryConfig(OptionFilename, Path: string): string;
     function GetValueFromSecondaryConfig(OptionFilename, Path: string): string;
     function GetValueFromIDEConfig(OptionFilename, Path: string): string;
    @@ -565,7 +596,7 @@
     
         // check $(LazarusDir)\fpc\bin\i386-win32\fpc.exe
         if CheckFile(SetDirSeparators('$(LazarusDir)/fpc/bin/$(TargetCPU)-$(TargetOS)/')+ShortCompFile,Result)
    -    then exit;
    +      then exit;
     
         // check common directories
         Files:=TStringList.Create;
    @@ -577,8 +608,8 @@
           Files.Free;
         end;
     
    +    // Windows-only locations:
         if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
    -      // Windows has some special places
           SysDrive:=GetEnvironmentVariableUTF8('SYSTEMDRIVE');
           if SysDrive='' then SysDrive:='C:';
           SysDrive:=AppendPathDelim(SysDrive);
    @@ -842,6 +873,165 @@
       end;
     end;
     
    +function CheckDebuggerQuality(AFilename: string; out Note: string
    +  ): TSDFilenameQuality;
    +begin
    +  Result:=sddqInvalid;
    +  AFilename:=TrimFilename(AFilename);
    +  if not FileExistsCached(AFilename) then
    +  begin
    +    Note:=lisFileNotFound4;
    +    exit;
    +  end;
    +  if DirPathExistsCached(AFilename) then
    +  begin
    +    Note:=lisFileIsDirectory;
    +    exit;
    +  end;
    +  if not FileIsExecutableCached(AFilename) then
    +  begin
    +    Note:=lisFileIsNotAnExecutable;
    +    exit;
    +  end;
    +
    +  { We could call gdb and parse the output looking for something like
    +  GNU gdb, but that may be going too far. }
    +  Note:=lisOk;
    +  Result:=sddqCompatible;
    +end;
    +
    +function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList;
    +
    +  function CheckFile(AFilename: string; var List: TObjectList): boolean;
    +  var
    +    Item: TSDFileInfo;
    +    RealFilename: String;
    +  begin
    +    Result:=false;
    +    if AFilename='' then exit;
    +    DoDirSeparators(AFilename);
    +    // check if already checked
    +    if CaptionInSDFileList(AFilename,List) then exit;
    +    EnvironmentOptions.DebuggerFilename:=AFilename;
    +    RealFilename:=EnvironmentOptions.GetParsedDebuggerFilename;
    +    debugln(['SearchDebuggerCandidates Value=',AFilename,' File=',RealFilename]);
    +    if RealFilename='' then exit;
    +    // check if exists
    +    if not FileExistsCached(RealFilename) then exit;
    +    // add to list and check quality
    +    Item:=TSDFileInfo.Create;
    +    Item.Filename:=RealFilename;
    +    Item.Quality:=CheckDebuggerQuality(RealFilename,Item.Note);
    +    Item.Caption:=AFilename;
    +    if List=nil then
    +      List:=TObjectList.create(true);
    +    List.Add(Item);
    +    Result:=(Item.Quality=sddqCompatible) and StopIfFits;
    +  end;
    +const
    +  DebuggerFileName='gdb'; //For Windows, .exe will be appended
    +var
    +  OldDebuggerFilename: String;
    +  AFilename: String;
    +  Files: TStringList;
    +  i: Integer;
    +begin
    +  Result:=nil;
    +
    +  OldDebuggerFilename:=EnvironmentOptions.DebuggerFilename;
    +  try
    +    // check current setting
    +    if CheckFile(EnvironmentOptions.DebuggerFilename,Result) then exit;
    +
    +    // check the primary options
    +    AFilename:=GetValueFromPrimaryConfig(EnvOptsConfFileName,
    +                                    'EnvironmentOptions/DebuggerFilename/Value');
    +    if CheckFile(AFilename,Result) then exit;
    +
    +    // check the secondary options
    +    AFilename:=GetValueFromSecondaryConfig(EnvOptsConfFileName,
    +                                    'EnvironmentOptions/DebuggerFilename/Value');
    +    if CheckFile(AFilename,Result) then exit;
    +
    +    // The next 2 locations are locations used by older and newer versions of the Windows installers
    +    // If other platform installers follow the same strategy, this can be useful.
    +    // Chances of this are low (gdb is generally installed in the path on Unixy systems), but it can't hurt...
    +    // and it can be useful for cross compiling/custom setups.
    +
    +    // Check new installation location: $(LazarusDir)\mingw\$(TargetCPU)-$(TargetOS)\bin\gdb.exe
    +    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/$(TargetCPU)-$(TargetOS)/bin/'+DebuggerFileName+GetExecutableExt),Result)
    +      then exit;
    +
    +    // Older Lazarus installers did not use macros for their debuggers: there was only one debugger
    +    // Check old installation location: $(LazarusDir)\mingw\bin\gdb.exe
    +    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/bin/'+DebuggerFileName+GetExecutableExt),Result)
    +      then exit;
    +
    +    // Windows-only locations:
    +    if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
    +      // check for debugger in fpc.exe directory - could be a lucky shot
    +      if CheckFile(SetDirSeparators('$Path($(CompPath))/'+DebuggerFileName+GetExecutableExt),Result)
    +        then exit;
    +    end;
    +
    +    // check history
    +    Files:=EnvironmentOptions.DebuggerFileHistory;
    +    if Files<>nil then
    +      for i:=0 to Files.Count-1 do
    +        if CheckFile(Files[i],Result) then exit;
    +
    +    // check PATH
    +    AFilename:=DebuggerFileName;
    +    AFilename+=GetExecutableExt;
    +    if CheckFile(FindDefaultExecutablePath(AFilename),Result) then exit;
    +
    +    // There are no common directories apart from the PATH
    +    // where gdb would be installed. Otherwise we could do something similar as
    +    // in SearchMakeExeCandidates.
    +  finally
    +    EnvironmentOptions.DebuggerFilename:=OldDebuggerFilename;
    +  end;
    +end;
    +
    +procedure SetupDebugger;
    +var
    +  Note: string;
    +  Filename: String;
    +  Quality: TSDFilenameQuality;
    +  BestDir: TSDFileInfo;
    +  List: TObjectList;
    +begin
    +  Filename:=EnvironmentOptions.GetParsedDebuggerFilename;
    +  Quality:=CheckDebuggerQuality(Filename,Note);
    +  if Quality<>sddqInvalid then exit;
    +  // bad debugger
    +  dbgout('SetupDebugger:');
    +  if EnvironmentOptions.DebuggerFilename<>'' then
    +  begin
    +    dbgout(' The "gdb" executable "',EnvironmentOptions.DebuggerFilename,'"');
    +    if EnvironmentOptions.DebuggerFilename<>Filename then
    +      dbgout(' => "',Filename,'"');
    +    dbgout(' is invalid (Error: ',Note,')');
    +    debugln(' Searching a proper one ...');
    +  end else begin
    +    debugln(' Searching "gdb" ...');
    +  end;
    +  List:=SearchDebuggerCandidates(true);
    +  try
    +    BestDir:=nil;
    +    if List<>nil then
    +      BestDir:=TSDFileInfo(List[List.Count-1]);
    +    if (BestDir=nil) or (BestDir.Quality=sddqInvalid) then begin
    +      debugln(['SetupDebugger: no proper "gdb" found.']);
    +      exit;
    +    end;
    +    EnvironmentOptions.DebuggerFilename:=BestDir.Filename;
    +    debugln(['SetupDebugger: using ',EnvironmentOptions.DebuggerFilename]);
    +  finally
    +    List.Free;
    +  end;
    +end;
    +
     function CheckMakeExeQuality(AFilename: string; out Note: string
       ): TSDFilenameQuality;
     begin
    @@ -863,11 +1053,13 @@
         exit;
       end;
     
    +  // Windows-only locations:
       if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
    -    // under Windows the make.exe is in the same directory as fpc.exe
    +    // under Windows, make.exe is in the same directory as fpc.exe
         if not FileExistsCached(ExtractFilePath(AFilename)+'fpc.exe') then begin
    -      Note:='There is no fpc.exe in the directory of the '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the fpc compiler.';
    +      Note:='There is no fpc.exe in the directory of '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the FPC compiler.';
           Result:=sddqIncomplete;
    +      exit;
         end;
       end;
     
    @@ -926,6 +1118,7 @@
                                         'EnvironmentOptions/MakeFilename/Value');
         if CheckFile(AFilename,Result) then exit;
     
    +    // Windows-only locations:
         if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
           // check make in fpc.exe directory
           if CheckFile(SetDirSeparators('$Path($(CompPath))/make.exe'),Result)
    @@ -1098,6 +1291,8 @@
       LazarusTabSheet.Caption:='Lazarus';
       CompilerTabSheet.Caption:=lisCompiler;
       FPCSourcesTabSheet.Caption:=lisFPCSources;
    +  MakeExeTabSheet.Caption:='make';
    +  DebuggerTabSheet.Caption:=lisDebugger;
     
       FHeadGraphic:=TPortableNetworkGraphic.Create;
       FHeadGraphic.LoadFromLazarusResource('ide_icon48x48');
    @@ -1105,6 +1300,8 @@
       TVNodeLazarus:=PropertiesTreeView.Items.Add(nil,LazarusTabSheet.Caption);
       TVNodeCompiler:=PropertiesTreeView.Items.Add(nil,CompilerTabSheet.Caption);
       TVNodeFPCSources:=PropertiesTreeView.Items.Add(nil,FPCSourcesTabSheet.Caption);
    +  TVNodeMakeExe:=PropertiesTreeView.Items.Add(nil,MakeExeTabSheet.Caption);
    +  TVNodeDebugger:=PropertiesTreeView.Items.Add(nil,DebuggerTabSheet.Caption);
       ImgIDError := ImageList1.AddLazarusResource('state_error');
       ImgIDWarning := ImageList1.AddLazarusResource('state_warning');
     
    @@ -1122,6 +1319,15 @@
       FPCSrcDirLabel.Caption:=Format(
         lisTheSourcesOfTheFreePascalPackagesAreRequiredForBro, [SetDirSeparators('rtl'
         +'/linux/system.pp')]);
    +
    +  MakeExeBrowseButton.Caption:=lisPathEditBrowse;
    +  MakeExeLabel.Caption:=Format(
    +    lisTheMakeExecutableTypicallyHasTheName, ['make'+GetExecutableExt('')]);
    +
    +  DebuggerBrowseButton.Caption:=lisPathEditBrowse;
    +  DebuggerLabel.Caption:=Format(
    +    lisTheDebuggerExecutableTypicallyHasTheName, ['gdb'+GetExecutableExt('')]);
    +
     end;
     
     procedure TInitialSetupDialog.CompilerComboBoxChange(Sender: TObject);
    @@ -1129,6 +1335,35 @@
       UpdateCompilerNote;
     end;
     
    +procedure TInitialSetupDialog.DebuggerBrowseButtonClick(Sender: TObject);
    +var
    +  Filename: String;
    +  Dlg: TOpenDialog;
    +  Filter: String;
    +begin
    +  Dlg:=TOpenDialog.Create(nil);
    +  try
    +    Filename:='gdb'+GetExecutableExt;
    +    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
    +    Dlg.Options:=Dlg.Options+[ofFileMustExist];
    +    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
    +    if ExtractFileExt(Filename)<>'' then
    +      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
    +    Dlg.Filter:=Filter;
    +    if not Dlg.Execute then exit;
    +    Filename:=Dlg.FileName;
    +  finally
    +    Dlg.Free;
    +  end;
    +  DebuggerComboBox.Text:=Filename;
    +  UpdateDebuggerNote;
    +end;
    +
    +procedure TInitialSetupDialog.DebuggerComboBoxChange(Sender: TObject);
    +begin
    +  UpdateDebuggerNote;
    +end;
    +
     procedure TInitialSetupDialog.CompilerBrowseButtonClick(Sender: TObject);
     var
       Filename: String;
    @@ -1193,6 +1428,35 @@
       UpdateLazDirNote;
     end;
     
    +procedure TInitialSetupDialog.MakeExeBrowseButtonClick(Sender: TObject);
    +var
    +  Filename: String;
    +  Dlg: TOpenDialog;
    +  Filter: String;
    +begin
    +  Dlg:=TOpenDialog.Create(nil);
    +  try
    +    Filename:='make'+GetExecutableExt;
    +    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
    +    Dlg.Options:=Dlg.Options+[ofFileMustExist];
    +    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
    +    if ExtractFileExt(Filename)<>'' then
    +      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
    +    Dlg.Filter:=Filter;
    +    if not Dlg.Execute then exit;
    +    Filename:=Dlg.FileName;
    +  finally
    +    Dlg.Free;
    +  end;
    +  MakeExeComboBox.Text:=Filename;
    +  UpdateMakeExeNote;
    +end;
    +
    +procedure TInitialSetupDialog.MakeExeComboBoxChange(Sender: TObject);
    +begin
    +  UpdateMakeExeNote;
    +end;
    +
     procedure TInitialSetupDialog.PropertiesPageControlChange(Sender: TObject);
     var
       s: String;
    @@ -1225,7 +1489,11 @@
       else if Node=TVNodeCompiler then
         s:=lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW
       else if Node=TVNodeFPCSources then
    -    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio;
    +    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio
    +  else if Node=TVNodeMakeExe then
    +    s:=lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp
    +  else if Node=TVNodeDebugger then
    +    s:=lisWithoutAProperDebuggerDebuggingWillBeDisappointing;
       if s<>'' then begin
         MsgResult:=MessageDlg(lisCCOWarningCaption, s, mtWarning, [mbIgnore,
           mbCancel], 0);
    @@ -1241,9 +1509,13 @@
       s:=FPCSrcDirComboBox.Text;
       if s<>'' then
         EnvironmentOptions.FPCSourceDirectory:=s;
    +  s:=MakeExeComboBox.Text;
    +  if s<>'' then
    +    EnvironmentOptions.MakeFilename:=s;
    +  s:=DebuggerComboBox.Text;
    +  if s<>'' then
    +    EnvironmentOptions.DebuggerFilename:=s;
     
    -  SetupMakeExe;
    -
       ModalResult:=mrOk;
     end;
     
    @@ -1267,6 +1539,12 @@
       end else if fCompilerFilenameChanged then begin
         UpdateFPCSrcDirCandidates;
         UpdateFPCSrcDirNote;
    +  end else if fMakeExeFilenameChanged then begin
    +    UpdateMakeExeCandidates;
    +    UpdateMakeExeNote;
    +  end else if fDebuggerFilenameChanged then begin
    +    UpdateDebuggerCandidates;
    +    UpdateDebuggerNote;
       end else
         IdleConnected:=false;
     end;
    @@ -1341,6 +1619,28 @@
       FillComboboxWithFileInfoList(FPCSrcDirComboBox,Dirs);
     end;
     
    +procedure TInitialSetupDialog.UpdateMakeExeCandidates;
    +var
    +  Files: TObjectList;
    +begin
    +  FLazarusDirChanged:=false;
    +  Files:=SearchMakeExeCandidates(false);
    +  FreeAndNil(FCandidates[sddtMakeExeFileName]);
    +  FCandidates[sddtMakeExeFileName]:=Files;
    +  FillComboboxWithFileInfoList(MakeExeComboBox,Files);
    +end;
    +
    +procedure TInitialSetupDialog.UpdateDebuggerCandidates;
    +var
    +  Files: TObjectList;
    +begin
    +  FLazarusDirChanged:=false;
    +  Files:=SearchDebuggerCandidates(false);
    +  FreeAndNil(FCandidates[sddtDebuggerFilename]);
    +  FCandidates[sddtDebuggerFilename]:=Files;
    +  FillComboboxWithFileInfoList(DebuggerComboBox,Files);
    +end;
    +
     procedure TInitialSetupDialog.FillComboboxWithFileInfoList(ABox: TComboBox;
       List: TObjectList; ItemIndex: integer);
     var
    @@ -1479,6 +1779,76 @@
       TVNodeFPCSources.SelectedIndex:=ImageIndex;
     end;
     
    +procedure TInitialSetupDialog.UpdateMakeExeNote;
    +var
    +  CurCaption: String;
    +  Note: string;
    +  Quality: TSDFilenameQuality;
    +  s: String;
    +  ImageIndex: Integer;
    +begin
    +  if csDestroying in ComponentState then exit;
    +  CurCaption:=MakeExeComboBox.Text;
    +  EnvironmentOptions.MakeFilename:=CurCaption;
    +  if fLastParsedMakeExe=EnvironmentOptions.GetParsedMakeFilename then exit;
    +  fLastParsedMakeExe:=EnvironmentOptions.GetParsedMakeFilename;
    +  //debugln(['TInitialSetupDialog.UpdateMakeExeNote ',fLastParsedMakeExe]);
    +  Quality:=CheckMakeExeQuality(fLastParsedMakeExe,Note);
    +
    +  case Quality of
    +  sddqInvalid: s:=lisError;
    +  sddqCompatible: s:='';
    +  else s:=lisWarning;
    +  end;
    +  if EnvironmentOptions.MakeFilename<>EnvironmentOptions.GetParsedMakeFilename
    +  then
    +    s:=lisFile2+EnvironmentOptions.GetParsedMakeFilename+LineEnding+
    +      LineEnding+s;
    +  MakeExeMemo.Text:=s+Note;
    +
    +  ImageIndex:=QualityToImgIndex(Quality);
    +  TVNodeMakeExe.ImageIndex:=ImageIndex;
    +  TVNodeMakeExe.SelectedIndex:=ImageIndex;
    +
    +  fMakeExeFilenameChanged:=true;
    +  IdleConnected:=true;
    +end;
    +
    +procedure TInitialSetupDialog.UpdateDebuggerNote;
    +var
    +  CurCaption: String;
    +  Note: string;
    +  Quality: TSDFilenameQuality;
    +  s: String;
    +  ImageIndex: Integer;
    +begin
    +  if csDestroying in ComponentState then exit;
    +  CurCaption:=DebuggerComboBox.Text;
    +  EnvironmentOptions.DebuggerFilename:=CurCaption;
    +  if fLastParsedDebugger=EnvironmentOptions.GetParsedDebuggerFilename then exit;
    +  fLastParsedDebugger:=EnvironmentOptions.GetParsedDebuggerFilename;
    +  //debugln(['TInitialSetupDialog.UpdateDebuggerNote ',fLastParsedDebugger]);
    +  Quality:=CheckDebuggerQuality(fLastParsedDebugger,Note);
    +
    +  case Quality of
    +  sddqInvalid: s:=lisError;
    +  sddqCompatible: s:='';
    +  else s:=lisWarning;
    +  end;
    +  if EnvironmentOptions.DebuggerFilename<>EnvironmentOptions.GetParsedDebuggerFilename
    +  then
    +    s:=lisFile2+EnvironmentOptions.GetParsedDebuggerFilename+LineEnding+
    +      LineEnding+s;
    +  DebuggerMemo.Text:=s+Note;
    +
    +  ImageIndex:=QualityToImgIndex(Quality);
    +  TVNodeDebugger.ImageIndex:=ImageIndex;
    +  TVNodeDebugger.SelectedIndex:=ImageIndex;
    +
    +  fDebuggerFilenameChanged:=true;
    +  IdleConnected:=true;
    +end;
    +
     function TInitialSetupDialog.FirstErrorNode: TTreeNode;
     var
       i: Integer;
    @@ -1518,6 +1888,8 @@
         Result:=-1
       else if Quality=sddqWrongMinorVersion then
         Result:=ImgIDWarning
    +  else if Quality=sddqIncomplete then
    +    Result:=ImgIDWarning
       else
         Result:=ImgIDError;
     end;
    @@ -1568,6 +1940,32 @@
       fLastParsedFPCSrcDir:='. .';
       UpdateFPCSrcDirNote;
     
    +  // Make executable
    +  UpdateMakeExeCandidates;
    +  if (not FileExistsCached(EnvironmentOptions.Filename)) then
    +  begin
    +    // first start => choose first best candidate
    +    Candidate:=GetFirstCandidate(FCandidates[sddtMakeExeFilename]);
    +    if Candidate<>nil then
    +      EnvironmentOptions.MakeFilename:=Candidate.Caption;
    +  end;
    +  MakeExeComboBox.Text:=EnvironmentOptions.MakeFilename;
    +  fLastParsedMakeExe:='. .';
    +  UpdateMakeExeNote;
    +
    +  // Debugger
    +  UpdateDebuggerCandidates;
    +  if (not FileExistsCached(EnvironmentOptions.Filename)) then
    +  begin
    +    // first start => choose first best candidate
    +    Candidate:=GetFirstCandidate(FCandidates[sddtDebuggerFilename]);
    +    if Candidate<>nil then
    +      EnvironmentOptions.DebuggerFilename:=Candidate.Caption;
    +  end;
    +  DebuggerComboBox.Text:=EnvironmentOptions.DebuggerFilename;
    +  fLastParsedDebugger:='. .';
    +  UpdateDebuggerNote;
    +
       // select first error
       Node:=FirstErrorNode;
       if Node=nil then
    Index: ide/lazarusidestrconsts.pas
    ===================================================================
    --- ide/lazarusidestrconsts.pas	(revision 38091)
    +++ ide/lazarusidestrconsts.pas	(working copy)
    @@ -2008,6 +2008,7 @@
       dlgCOLibraries = 'Libraries (-Fl):';
       dlgCODebugPath = 'Debugger path addition (none):';
       lisCompiler = 'Compiler';
    +  lisDebugger = 'Debugger';
       lisToFPCPath = 'Path:';
       lisCOSkipCallingCompiler = 'Skip calling compiler';
       lisCOAmbiguousAdditionalCompilerConfigFile = 'Ambiguous additional compiler '
    @@ -5437,6 +5438,10 @@
         +'Lazarus directory you will get a lot of warnings.';
       lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW = 'Without a proper '
         +'compiler the code browsing and compiling will be disappointing.';
    +  lisWithoutAProperDebuggerDebuggingWillBeDisappointing = 'Without a proper '
    +    +'debugger, debugging will be disappointing.';
    +  lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp = 'Without a proper '
    +    +'make executable the code browsing and compiling will be disappointing.';
       lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio = 'Without the proper '
         +'FPC sources code browsing and completion will be very limited.';
       lisTheLazarusDirectoryContainsTheSourcesOfTheIDEAndTh = 'The Lazarus '
    @@ -5446,6 +5451,11 @@
       lisTheFreePascalCompilerExecutableTypicallyHasTheName = 'The Free Pascal '
         +'compiler executable typically has the name "%s". You can also use the '
         +'target specific compiler like "%s". Please give the full file path.';
    +  lisTheMakeExecutableTypicallyHasTheName = 'The make executable typically '
    +    +'has the name "%s". Please give the full file path.';
    +  lisTheDebuggerExecutableTypicallyHasTheName = 'The debugger executable '
    +    +'typically has the name "%s". Pleae give the full file path. '
    +    +'A useful setting on Windows systems is: $(LazarusDir)\mingw\bin\$(TargetCPU)-$(TargetOS)\gdb.exe';
       lisFoundVersionExpected = 'Found version %s, expected %s';
       lisInvalidVersionIn = 'invalid version in %s';
       lisWrongVersionIn = 'wrong version in %s: %s';
    
  • initial_checkdebugger3.diff (36,180 bytes)
    Index: ide/initialsetupdlgs.lfm
    ===================================================================
    --- ide/initialsetupdlgs.lfm	(revision 38091)
    +++ ide/initialsetupdlgs.lfm	(working copy)
    @@ -1,8 +1,8 @@
     object InitialSetupDialog: TInitialSetupDialog
       AnchorSideBottom.Side = asrBottom
    -  Left = 253
    +  Left = 319
       Height = 385
    -  Top = 253
    +  Top = 238
       Width = 620
       Caption = 'InitialSetupDialog'
       ClientHeight = 385
    @@ -10,7 +10,7 @@
       OnCreate = FormCreate
       OnDestroy = FormDestroy
       Position = poScreenCenter
    -  LCLVersion = '0.9.31'
    +  LCLVersion = '1.1'
       object PropertiesTreeView: TTreeView
         AnchorSideLeft.Control = Owner
         AnchorSideTop.Control = WelcomePaintBox
    @@ -18,7 +18,7 @@
         AnchorSideRight.Control = Splitter1
         AnchorSideBottom.Control = BtnPanel
         Left = 6
    -    Height = 289
    +    Height = 286
         Top = 54
         Width = 159
         Anchors = [akTop, akLeft, akRight, akBottom]
    @@ -40,7 +40,7 @@
         AnchorSideBottom.Control = PropertiesTreeView
         AnchorSideBottom.Side = asrBottom
         Left = 165
    -    Height = 289
    +    Height = 286
         Top = 54
         Width = 5
         Align = alNone
    @@ -48,21 +48,21 @@
       end
       object BtnPanel: TPanel
         Left = 10
    -    Height = 22
    -    Top = 353
    +    Height = 25
    +    Top = 350
         Width = 600
         Align = alBottom
         AutoSize = True
         BorderSpacing.Around = 10
         BevelOuter = bvNone
    -    ClientHeight = 22
    +    ClientHeight = 25
         ClientWidth = 600
         TabOrder = 2
         object StartIDEBitBtn: TBitBtn
    -      Left = 489
    -      Height = 22
    +      Left = 500
    +      Height = 25
           Top = 0
    -      Width = 111
    +      Width = 100
           Align = alRight
           AutoSize = True
           Caption = 'StartIDEBitBtn'
    @@ -80,13 +80,13 @@
         AnchorSideBottom.Control = Splitter1
         AnchorSideBottom.Side = asrBottom
         Left = 170
    -    Height = 289
    +    Height = 286
         Top = 54
         Width = 444
    -    ActivePage = FPCSourcesTabSheet
    +    ActivePage = LazarusTabSheet
         Anchors = [akTop, akLeft, akRight, akBottom]
         BorderSpacing.Right = 6
    -    TabIndex = 2
    +    TabIndex = 0
         TabOrder = 3
         OnChange = PropertiesPageControlChange
         Options = [nboHidePageListPopup]
    @@ -96,11 +96,11 @@
           ChildSizing.TopBottomSpacing = 6
           ChildSizing.HorizontalSpacing = 6
           ChildSizing.VerticalSpacing = 6
    -      ClientHeight = 255
    -      ClientWidth = 442
    +      ClientHeight = 258
    +      ClientWidth = 436
           object LazDirLabel: TLabel
             Left = 6
    -        Height = 14
    +        Height = 15
             Top = 6
             Width = 424
             Align = alTop
    @@ -115,11 +115,11 @@
             AnchorSideRight.Control = LazarusTabSheet
             AnchorSideRight.Side = asrBottom
             Left = 6
    -        Height = 21
    -        Top = 26
    +        Height = 23
    +        Top = 27
             Width = 424
             Anchors = [akTop, akLeft, akRight]
    -        ItemHeight = 0
    +        ItemHeight = 15
             OnChange = LazDirComboBoxChange
             TabOrder = 0
             Text = 'LazDirComboBox'
    @@ -128,8 +128,8 @@
             AnchorSideTop.Control = LazDirBrowseButton
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 174
    -        Top = 82
    +        Height = 165
    +        Top = 87
             Width = 424
             Align = alBottom
             Anchors = [akTop, akLeft, akRight, akBottom]
    @@ -148,9 +148,9 @@
             AnchorSideTop.Side = asrBottom
             AnchorSideRight.Side = asrBottom
             Left = 6
    -        Height = 23
    -        Top = 53
    -        Width = 122
    +        Height = 25
    +        Top = 56
    +        Width = 132
             AutoSize = True
             Caption = 'LazDirBrowseButton'
             OnClick = LazDirBrowseButtonClick
    @@ -163,13 +163,13 @@
           ChildSizing.TopBottomSpacing = 6
           ChildSizing.HorizontalSpacing = 6
           ChildSizing.VerticalSpacing = 6
    -      ClientHeight = 250
    -      ClientWidth = 438
    +      ClientHeight = 258
    +      ClientWidth = 436
           object CompilerLabel: TLabel
             Left = 6
    -        Height = 17
    +        Height = 15
             Top = 6
    -        Width = 426
    +        Width = 424
             Align = alTop
             Caption = 'CompilerLabel'
             ParentColor = False
    @@ -182,11 +182,11 @@
             AnchorSideRight.Control = CompilerTabSheet
             AnchorSideRight.Side = asrBottom
             Left = 6
    -        Height = 21
    -        Top = 29
    -        Width = 426
    +        Height = 23
    +        Top = 27
    +        Width = 424
             Anchors = [akTop, akLeft, akRight]
    -        ItemHeight = 0
    +        ItemHeight = 15
             OnChange = CompilerComboBoxChange
             TabOrder = 0
             Text = 'CompilerComboBox'
    @@ -196,9 +196,9 @@
             AnchorSideTop.Control = CompilerComboBox
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 20
    +        Height = 25
             Top = 56
    -        Width = 168
    +        Width = 149
             AutoSize = True
             Caption = 'CompilerBrowseButton'
             OnClick = CompilerBrowseButtonClick
    @@ -213,9 +213,9 @@
             AnchorSideBottom.Control = CompilerTabSheet
             AnchorSideBottom.Side = asrBottom
             Left = 6
    -        Height = 162
    -        Top = 82
    -        Width = 426
    +        Height = 165
    +        Top = 87
    +        Width = 424
             Anchors = [akTop, akLeft, akRight, akBottom]
             Lines.Strings = (
               'CompilerMemo'
    @@ -232,13 +232,13 @@
           ChildSizing.TopBottomSpacing = 6
           ChildSizing.HorizontalSpacing = 6
           ChildSizing.VerticalSpacing = 6
    -      ClientHeight = 250
    -      ClientWidth = 438
    +      ClientHeight = 258
    +      ClientWidth = 436
           object FPCSrcDirLabel: TLabel
             Left = 6
    -        Height = 17
    +        Height = 15
             Top = 6
    -        Width = 426
    +        Width = 424
             Align = alTop
             Caption = 'FPCSrcDirLabel'
             ParentColor = False
    @@ -246,11 +246,11 @@
           end
           object FPCSrcDirComboBox: TComboBox
             Left = 6
    -        Height = 21
    -        Top = 29
    -        Width = 426
    +        Height = 23
    +        Top = 27
    +        Width = 424
             Align = alTop
    -        ItemHeight = 0
    +        ItemHeight = 15
             OnChange = FPCSrcDirComboBoxChange
             TabOrder = 0
             Text = 'FPCSrcDirComboBox'
    @@ -260,9 +260,9 @@
             AnchorSideTop.Control = FPCSrcDirComboBox
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 20
    +        Height = 25
             Top = 56
    -        Width = 171
    +        Width = 152
             AutoSize = True
             Caption = 'FPCSrcDirBrowseButton'
             OnClick = FPCSrcDirBrowseButtonClick
    @@ -272,9 +272,9 @@
             AnchorSideTop.Control = FPCSrcDirBrowseButton
             AnchorSideTop.Side = asrBottom
             Left = 6
    -        Height = 162
    -        Top = 82
    -        Width = 426
    +        Height = 165
    +        Top = 87
    +        Width = 424
             Align = alBottom
             Anchors = [akTop, akLeft, akRight, akBottom]
             Lines.Strings = (
    @@ -286,6 +286,118 @@
             TabOrder = 2
           end
         end
    +    object MakeExeTabSheet: TTabSheet
    +      Caption = 'MakeExeTabSheet'
    +      ClientHeight = 258
    +      ClientWidth = 436
    +      object MakeExeComboBox: TComboBox
    +        Left = 0
    +        Height = 23
    +        Top = 15
    +        Width = 436
    +        Align = alTop
    +        ItemHeight = 15
    +        OnChange = MakeExeComboBoxChange
    +        TabOrder = 0
    +        Text = 'MakeExeComboBox'
    +      end
    +      object MakeExeLabel: TLabel
    +        Left = 0
    +        Height = 15
    +        Top = 0
    +        Width = 436
    +        Align = alTop
    +        Caption = 'MakeExeLabel'
    +        ParentColor = False
    +        WordWrap = True
    +      end
    +      object MakeExeBrowseButton: TButton
    +        AnchorSideLeft.Control = FPCSourcesTabSheet
    +        AnchorSideTop.Control = MakeExeComboBox
    +        AnchorSideTop.Side = asrBottom
    +        Left = 6
    +        Height = 25
    +        Top = 38
    +        Width = 146
    +        AutoSize = True
    +        Caption = 'MakeExeBrowseButton'
    +        OnClick = MakeExeBrowseButtonClick
    +        TabOrder = 1
    +      end
    +      object MakeExeMemo: TMemo
    +        AnchorSideTop.Control = MakeExeBrowseButton
    +        AnchorSideTop.Side = asrBottom
    +        Left = 0
    +        Height = 195
    +        Top = 63
    +        Width = 436
    +        Align = alBottom
    +        Anchors = [akTop, akLeft, akRight, akBottom]
    +        Lines.Strings = (
    +          'FPCSrcDirMemo'
    +          ''
    +          ''
    +        )
    +        ReadOnly = True
    +        TabOrder = 2
    +      end
    +    end
    +    object DebuggerTabSheet: TTabSheet
    +      Caption = 'DebuggerTabSheet'
    +      ClientHeight = 258
    +      ClientWidth = 436
    +      object DebuggerComboBox: TComboBox
    +        Left = 0
    +        Height = 23
    +        Top = 15
    +        Width = 436
    +        Align = alTop
    +        ItemHeight = 15
    +        OnChange = DebuggerComboBoxChange
    +        TabOrder = 0
    +        Text = 'DebuggerComboBox'
    +      end
    +      object DebuggerLabel: TLabel
    +        Left = 0
    +        Height = 15
    +        Top = 0
    +        Width = 436
    +        Align = alTop
    +        Caption = 'DebuggerLabel'
    +        ParentColor = False
    +        WordWrap = True
    +      end
    +      object DebuggerBrowseButton: TButton
    +        AnchorSideLeft.Control = FPCSourcesTabSheet
    +        AnchorSideTop.Control = DebuggerComboBox
    +        AnchorSideTop.Side = asrBottom
    +        Left = 6
    +        Height = 25
    +        Top = 38
    +        Width = 152
    +        AutoSize = True
    +        Caption = 'DebuggerBrowseButton'
    +        OnClick = DebuggerBrowseButtonClick
    +        TabOrder = 1
    +      end
    +      object DebuggerMemo: TMemo
    +        AnchorSideTop.Control = DebuggerBrowseButton
    +        AnchorSideTop.Side = asrBottom
    +        Left = 0
    +        Height = 195
    +        Top = 63
    +        Width = 436
    +        Align = alBottom
    +        Anchors = [akTop, akLeft, akRight, akBottom]
    +        Lines.Strings = (
    +          'FPCSrcDirMemo'
    +          ''
    +          ''
    +        )
    +        ReadOnly = True
    +        TabOrder = 2
    +      end
    +    end
       end
       object WelcomePaintBox: TPaintBox
         Left = 0
    Index: ide/initialsetupdlgs.pas
    ===================================================================
    --- ide/initialsetupdlgs.pas	(revision 38091)
    +++ ide/initialsetupdlgs.pas	(working copy)
    @@ -67,7 +67,9 @@
       TSDFilenameType = (
         sddtLazarusSrcDir,
         sddtCompilerFilename,
    -    sddtFPCSrcDir
    +    sddtFPCSrcDir,
    +    sddtMakeExeFilename,
    +    sddtDebuggerFilename
         );
     
       { TInitialSetupDialog }
    @@ -79,9 +81,17 @@
         CompilerLabel: TLabel;
         CompilerMemo: TMemo;
         FPCSrcDirBrowseButton: TButton;
    +    MakeExeBrowseButton: TButton;
    +    DebuggerBrowseButton: TButton;
         FPCSrcDirComboBox: TComboBox;
    +    MakeExeComboBox: TComboBox;
    +    DebuggerComboBox: TComboBox;
         FPCSrcDirLabel: TLabel;
    +    MakeExeLabel: TLabel;
    +    DebuggerLabel: TLabel;
         FPCSrcDirMemo: TMemo;
    +    MakeExeMemo: TMemo;
    +    DebuggerMemo: TMemo;
         ImageList1: TImageList;
         LazDirBrowseButton: TButton;
         LazDirLabel: TLabel;
    @@ -94,15 +104,21 @@
         LazarusTabSheet: TTabSheet;
         CompilerTabSheet: TTabSheet;
         FPCSourcesTabSheet: TTabSheet;
    +    MakeExeTabSheet: TTabSheet;
    +    DebuggerTabSheet: TTabSheet;
         WelcomePaintBox: TPaintBox;
         procedure CompilerBrowseButtonClick(Sender: TObject);
         procedure CompilerComboBoxChange(Sender: TObject);
    +    procedure DebuggerBrowseButtonClick(Sender: TObject);
    +    procedure DebuggerComboBoxChange(Sender: TObject);
         procedure FormCreate(Sender: TObject);
         procedure FormDestroy(Sender: TObject);
         procedure FPCSrcDirBrowseButtonClick(Sender: TObject);
         procedure FPCSrcDirComboBoxChange(Sender: TObject);
         procedure LazDirBrowseButtonClick(Sender: TObject);
         procedure LazDirComboBoxChange(Sender: TObject);
    +    procedure MakeExeBrowseButtonClick(Sender: TObject);
    +    procedure MakeExeComboBoxChange(Sender: TObject);
         procedure PropertiesPageControlChange(Sender: TObject);
         procedure PropertiesTreeViewSelectionChanged(Sender: TObject);
         procedure StartIDEBitBtnClick(Sender: TObject);
    @@ -111,9 +127,13 @@
       private
         FLazarusDirChanged: boolean;
         fCompilerFilenameChanged: boolean;
    +    fMakeExeFilenameChanged: boolean;
    +    fDebuggerFilenameChanged: boolean;
         FLastParsedLazDir: string;
         fLastParsedCompiler: string;
         fLastParsedFPCSrcDir: string;
    +    fLastParsedMakeExe: string;
    +    fLastParsedDebugger: string;
         FIdleConnected: boolean;
         ImgIDError: LongInt;
         ImgIDWarning: LongInt;
    @@ -125,13 +145,17 @@
         procedure UpdateLazarusDirCandidates;
         procedure UpdateCompilerFilenameCandidates;
         procedure UpdateFPCSrcDirCandidates;
    +    procedure UpdateMakeExeCandidates;
    +    procedure UpdateDebuggerCandidates;
         procedure FillComboboxWithFileInfoList(ABox: TComboBox; List: TObjectList;
            ItemIndex: integer = 0);
         procedure SetIdleConnected(const AValue: boolean);
         procedure UpdateLazDirNote;
         procedure UpdateCompilerNote;
         procedure UpdateFPCSrcDirNote;
    -    function FirstErrorNode: TTreeNode;
    +    procedure UpdateMakeExeNote;
    +    procedure UpdateDebuggerNote;
    +    function FirstErrorNode(IncludeWarnings: boolean): TTreeNode; //Get first treeview node where an error is shown. If IncludeWarnings: return warning node if no error node found
         function GetFPCVer: string;
         function GetFirstCandidate(Candidates: TObjectList;
           MinQuality: TSDFilenameQuality = sddqCompatible): TSDFileInfo;
    @@ -140,7 +164,9 @@
         TVNodeLazarus: TTreeNode;
         TVNodeCompiler: TTreeNode;
         TVNodeFPCSources: TTreeNode;
    -    procedure Init;
    +    TVNodeMakeExe: TTreeNode;
    +    TVNodeDebugger: TTreeNode;
    +    procedure Init; //Check for config errors, find and show alternatives
         property IdleConnected: boolean read FIdleConnected write SetIdleConnected;
       end;
     
    @@ -164,10 +190,15 @@
     procedure SetupFPCSrcDir(FPCVer: string);
     
     function CheckMakeExeQuality(AFilename: string;
    -  out Note: string): TSDFilenameQuality;
    -function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList;
    -procedure SetupMakeExe;
    +  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid make executable
    +function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList; //Search make candidates and add them to the list, including quality level
    +procedure SetupMakeExe; //Checks if the make specified in user's options (if any) is ok. If not, search for and set a valid one if possible
     
    +function CheckDebuggerQuality(AFilename: string;
    +  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid debugger (only gdb supported for now)
    +function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList; //Search debugger candidates and add them to list, including quality level
    +procedure SetupDebugger; //Checks if the debugger specified in user's option (if any) is ok. If not, search for and set a valid one if possible
    +
     function GetValueFromPrimaryConfig(OptionFilename, Path: string): string;
     function GetValueFromSecondaryConfig(OptionFilename, Path: string): string;
     function GetValueFromIDEConfig(OptionFilename, Path: string): string;
    @@ -383,7 +414,7 @@
         if EnvironmentOptions.LazarusDirectory<>Dir then
           dbgout(' => "',Dir,'"');
         dbgout(' is invalid (Error: ',Note,')');
    -    debugln(' Searching a proper one ...');
    +    debugln(' Searching for a proper one ...');
       end else begin
         debugln(' Searching ...');
       end;
    @@ -565,7 +596,7 @@
     
         // check $(LazarusDir)\fpc\bin\i386-win32\fpc.exe
         if CheckFile(SetDirSeparators('$(LazarusDir)/fpc/bin/$(TargetCPU)-$(TargetOS)/')+ShortCompFile,Result)
    -    then exit;
    +      then exit;
     
         // check common directories
         Files:=TStringList.Create;
    @@ -577,8 +608,8 @@
           Files.Free;
         end;
     
    +    // Windows-only locations:
         if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
    -      // Windows has some special places
           SysDrive:=GetEnvironmentVariableUTF8('SYSTEMDRIVE');
           if SysDrive='' then SysDrive:='C:';
           SysDrive:=AppendPathDelim(SysDrive);
    @@ -616,7 +647,7 @@
         if EnvironmentOptions.CompilerFilename<>Filename then
           dbgout(' => "',Filename,'"');
         dbgout(' is invalid (Error: ',Note,')');
    -    debugln(' Searching a proper one ...');
    +    debugln(' Searching for a proper one ...');
       end else begin
         debugln(' Searching compiler ...');
       end;
    @@ -822,7 +853,7 @@
         if EnvironmentOptions.FPCSourceDirectory<>Dir then
           dbgout(' => "',Dir,'"');
         dbgout(' is invalid (Error: ',Note,')');
    -    debugln(' Searching a proper one ...');
    +    debugln(' Searching for a proper one ...');
       end else begin
         debugln(' Searching ...');
       end;
    @@ -842,6 +873,165 @@
       end;
     end;
     
    +function CheckDebuggerQuality(AFilename: string; out Note: string
    +  ): TSDFilenameQuality;
    +begin
    +  Result:=sddqInvalid;
    +  AFilename:=TrimFilename(AFilename);
    +  if not FileExistsCached(AFilename) then
    +  begin
    +    Note:=lisFileNotFound4;
    +    exit;
    +  end;
    +  if DirPathExistsCached(AFilename) then
    +  begin
    +    Note:=lisFileIsDirectory;
    +    exit;
    +  end;
    +  if not FileIsExecutableCached(AFilename) then
    +  begin
    +    Note:=lisFileIsNotAnExecutable;
    +    exit;
    +  end;
    +
    +  { We could call gdb and parse the output looking for something like
    +  GNU gdb, but that may be going too far. }
    +  Note:=lisOk;
    +  Result:=sddqCompatible;
    +end;
    +
    +function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList;
    +
    +  function CheckFile(AFilename: string; var List: TObjectList): boolean;
    +  var
    +    Item: TSDFileInfo;
    +    RealFilename: String;
    +  begin
    +    Result:=false;
    +    if AFilename='' then exit;
    +    DoDirSeparators(AFilename);
    +    // check if already checked
    +    if CaptionInSDFileList(AFilename,List) then exit;
    +    EnvironmentOptions.DebuggerFilename:=AFilename;
    +    RealFilename:=EnvironmentOptions.GetParsedDebuggerFilename;
    +    debugln(['SearchDebuggerCandidates Value=',AFilename,' File=',RealFilename]);
    +    if RealFilename='' then exit;
    +    // check if exists
    +    if not FileExistsCached(RealFilename) then exit;
    +    // add to list and check quality
    +    Item:=TSDFileInfo.Create;
    +    Item.Filename:=RealFilename;
    +    Item.Quality:=CheckDebuggerQuality(RealFilename,Item.Note);
    +    Item.Caption:=AFilename;
    +    if List=nil then
    +      List:=TObjectList.create(true);
    +    List.Add(Item);
    +    Result:=(Item.Quality=sddqCompatible) and StopIfFits;
    +  end;
    +const
    +  DebuggerFileName='gdb'; //For Windows, .exe will be appended
    +var
    +  OldDebuggerFilename: String;
    +  AFilename: String;
    +  Files: TStringList;
    +  i: Integer;
    +begin
    +  Result:=nil;
    +
    +  OldDebuggerFilename:=EnvironmentOptions.DebuggerFilename;
    +  try
    +    // check current setting
    +    if CheckFile(EnvironmentOptions.DebuggerFilename,Result) then exit;
    +
    +    // check the primary options
    +    AFilename:=GetValueFromPrimaryConfig(EnvOptsConfFileName,
    +                                    'EnvironmentOptions/DebuggerFilename/Value');
    +    if CheckFile(AFilename,Result) then exit;
    +
    +    // check the secondary options
    +    AFilename:=GetValueFromSecondaryConfig(EnvOptsConfFileName,
    +                                    'EnvironmentOptions/DebuggerFilename/Value');
    +    if CheckFile(AFilename,Result) then exit;
    +
    +    // The next 2 locations are locations used by older and newer versions of the Windows installers
    +    // If other platform installers follow the same strategy, this can be useful.
    +    // Chances of this are low (gdb is generally installed in the path on Unixy systems), but it can't hurt...
    +    // and it can be useful for cross compiling/custom setups.
    +
    +    // Check new installation location: $(LazarusDir)\mingw\$(TargetCPU)-$(TargetOS)\bin\gdb.exe
    +    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/$(TargetCPU)-$(TargetOS)/bin/'+DebuggerFileName+GetExecutableExt),Result)
    +      then exit;
    +
    +    // Older Lazarus installers did not use macros for their debuggers: there was only one debugger
    +    // Check old installation location: $(LazarusDir)\mingw\bin\gdb.exe
    +    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/bin/'+DebuggerFileName+GetExecutableExt),Result)
    +      then exit;
    +
    +    // Windows-only locations:
    +    if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
    +      // check for debugger in fpc.exe directory - could be a lucky shot
    +      if CheckFile(SetDirSeparators('$Path($(CompPath))/'+DebuggerFileName+GetExecutableExt),Result)
    +        then exit;
    +    end;
    +
    +    // check history
    +    Files:=EnvironmentOptions.DebuggerFileHistory;
    +    if Files<>nil then
    +      for i:=0 to Files.Count-1 do
    +        if CheckFile(Files[i],Result) then exit;
    +
    +    // check PATH
    +    AFilename:=DebuggerFileName;
    +    AFilename+=GetExecutableExt;
    +    if CheckFile(FindDefaultExecutablePath(AFilename),Result) then exit;
    +
    +    // There are no common directories apart from the PATH
    +    // where gdb would be installed. Otherwise we could do something similar as
    +    // in SearchMakeExeCandidates.
    +  finally
    +    EnvironmentOptions.DebuggerFilename:=OldDebuggerFilename;
    +  end;
    +end;
    +
    +procedure SetupDebugger;
    +var
    +  Note: string;
    +  Filename: String;
    +  Quality: TSDFilenameQuality;
    +  BestDir: TSDFileInfo;
    +  List: TObjectList;
    +begin
    +  Filename:=EnvironmentOptions.GetParsedDebuggerFilename;
    +  Quality:=CheckDebuggerQuality(Filename,Note);
    +  if Quality<>sddqInvalid then exit;
    +  // bad debugger
    +  dbgout('SetupDebugger:');
    +  if EnvironmentOptions.DebuggerFilename<>'' then
    +  begin
    +    dbgout(' The "gdb" executable "',EnvironmentOptions.DebuggerFilename,'"');
    +    if EnvironmentOptions.DebuggerFilename<>Filename then
    +      dbgout(' => "',Filename,'"');
    +    dbgout(' is invalid (Error: ',Note,')');
    +    debugln(' Searching for a proper one ...');
    +  end else begin
    +    debugln(' Searching "gdb" ...');
    +  end;
    +  List:=SearchDebuggerCandidates(true);
    +  try
    +    BestDir:=nil;
    +    if List<>nil then
    +      BestDir:=TSDFileInfo(List[List.Count-1]);
    +    if (BestDir=nil) or (BestDir.Quality=sddqInvalid) then begin
    +      debugln(['SetupDebugger: no proper "gdb" found.']);
    +      exit;
    +    end;
    +    EnvironmentOptions.DebuggerFilename:=BestDir.Filename;
    +    debugln(['SetupDebugger: using ',EnvironmentOptions.DebuggerFilename]);
    +  finally
    +    List.Free;
    +  end;
    +end;
    +
     function CheckMakeExeQuality(AFilename: string; out Note: string
       ): TSDFilenameQuality;
     begin
    @@ -863,14 +1053,17 @@
         exit;
       end;
     
    +  // Windows-only locations:
       if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
    -    // under Windows the make.exe is in the same directory as fpc.exe
    +    // under Windows, make.exe is in the same directory as fpc.exe
         if not FileExistsCached(ExtractFilePath(AFilename)+'fpc.exe') then begin
    -      Note:='There is no fpc.exe in the directory of the '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the fpc compiler.';
    +      Note:='There is no fpc.exe in the directory of '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the FPC compiler.';
           Result:=sddqIncomplete;
    +      exit;
         end;
       end;
     
    +  Note:=lisOK;
       Result:=sddqCompatible;
     end;
     
    @@ -926,6 +1119,7 @@
                                         'EnvironmentOptions/MakeFilename/Value');
         if CheckFile(AFilename,Result) then exit;
     
    +    // Windows-only locations:
         if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
           // check make in fpc.exe directory
           if CheckFile(SetDirSeparators('$Path($(CompPath))/make.exe'),Result)
    @@ -980,7 +1174,7 @@
         if EnvironmentOptions.MakeFilename<>Filename then
           dbgout(' => "',Filename,'"');
         dbgout(' is invalid (Error: ',Note,')');
    -    debugln(' Searching a proper one ...');
    +    debugln(' Searching for a proper one ...');
       end else begin
         debugln(' Searching "make" ...');
       end;
    @@ -1098,6 +1292,8 @@
       LazarusTabSheet.Caption:='Lazarus';
       CompilerTabSheet.Caption:=lisCompiler;
       FPCSourcesTabSheet.Caption:=lisFPCSources;
    +  MakeExeTabSheet.Caption:='make';
    +  DebuggerTabSheet.Caption:=lisDebugger;
     
       FHeadGraphic:=TPortableNetworkGraphic.Create;
       FHeadGraphic.LoadFromLazarusResource('ide_icon48x48');
    @@ -1105,6 +1301,8 @@
       TVNodeLazarus:=PropertiesTreeView.Items.Add(nil,LazarusTabSheet.Caption);
       TVNodeCompiler:=PropertiesTreeView.Items.Add(nil,CompilerTabSheet.Caption);
       TVNodeFPCSources:=PropertiesTreeView.Items.Add(nil,FPCSourcesTabSheet.Caption);
    +  TVNodeMakeExe:=PropertiesTreeView.Items.Add(nil,MakeExeTabSheet.Caption);
    +  TVNodeDebugger:=PropertiesTreeView.Items.Add(nil,DebuggerTabSheet.Caption);
       ImgIDError := ImageList1.AddLazarusResource('state_error');
       ImgIDWarning := ImageList1.AddLazarusResource('state_warning');
     
    @@ -1122,6 +1320,15 @@
       FPCSrcDirLabel.Caption:=Format(
         lisTheSourcesOfTheFreePascalPackagesAreRequiredForBro, [SetDirSeparators('rtl'
         +'/linux/system.pp')]);
    +
    +  MakeExeBrowseButton.Caption:=lisPathEditBrowse;
    +  MakeExeLabel.Caption:=Format(
    +    lisTheMakeExecutableTypicallyHasTheName, ['make'+GetExecutableExt('')]);
    +
    +  DebuggerBrowseButton.Caption:=lisPathEditBrowse;
    +  DebuggerLabel.Caption:=Format(
    +    lisTheDebuggerExecutableTypicallyHasTheName, ['gdb'+GetExecutableExt('')]);
    +
     end;
     
     procedure TInitialSetupDialog.CompilerComboBoxChange(Sender: TObject);
    @@ -1129,6 +1336,35 @@
       UpdateCompilerNote;
     end;
     
    +procedure TInitialSetupDialog.DebuggerBrowseButtonClick(Sender: TObject);
    +var
    +  Filename: String;
    +  Dlg: TOpenDialog;
    +  Filter: String;
    +begin
    +  Dlg:=TOpenDialog.Create(nil);
    +  try
    +    Filename:='gdb'+GetExecutableExt;
    +    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
    +    Dlg.Options:=Dlg.Options+[ofFileMustExist];
    +    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
    +    if ExtractFileExt(Filename)<>'' then
    +      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
    +    Dlg.Filter:=Filter;
    +    if not Dlg.Execute then exit;
    +    Filename:=Dlg.FileName;
    +  finally
    +    Dlg.Free;
    +  end;
    +  DebuggerComboBox.Text:=Filename;
    +  UpdateDebuggerNote;
    +end;
    +
    +procedure TInitialSetupDialog.DebuggerComboBoxChange(Sender: TObject);
    +begin
    +  UpdateDebuggerNote;
    +end;
    +
     procedure TInitialSetupDialog.CompilerBrowseButtonClick(Sender: TObject);
     var
       Filename: String;
    @@ -1193,6 +1429,35 @@
       UpdateLazDirNote;
     end;
     
    +procedure TInitialSetupDialog.MakeExeBrowseButtonClick(Sender: TObject);
    +var
    +  Filename: String;
    +  Dlg: TOpenDialog;
    +  Filter: String;
    +begin
    +  Dlg:=TOpenDialog.Create(nil);
    +  try
    +    Filename:='make'+GetExecutableExt;
    +    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
    +    Dlg.Options:=Dlg.Options+[ofFileMustExist];
    +    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
    +    if ExtractFileExt(Filename)<>'' then
    +      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
    +    Dlg.Filter:=Filter;
    +    if not Dlg.Execute then exit;
    +    Filename:=Dlg.FileName;
    +  finally
    +    Dlg.Free;
    +  end;
    +  MakeExeComboBox.Text:=Filename;
    +  UpdateMakeExeNote;
    +end;
    +
    +procedure TInitialSetupDialog.MakeExeComboBoxChange(Sender: TObject);
    +begin
    +  UpdateMakeExeNote;
    +end;
    +
     procedure TInitialSetupDialog.PropertiesPageControlChange(Sender: TObject);
     var
       s: String;
    @@ -1219,13 +1484,17 @@
       s: String;
       MsgResult: TModalResult;
     begin
    -  Node:=FirstErrorNode;
    +  Node:=FirstErrorNode(false);
       if Node=TVNodeLazarus then
         s:=lisWithoutAProperLazarusDirectoryYouWillGetALotOfWarn
       else if Node=TVNodeCompiler then
         s:=lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW
       else if Node=TVNodeFPCSources then
    -    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio;
    +    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio
    +  else if Node=TVNodeMakeExe then
    +    s:=lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp
    +  else if Node=TVNodeDebugger then
    +    s:=lisWithoutAProperDebuggerDebuggingWillBeDisappointing;
       if s<>'' then begin
         MsgResult:=MessageDlg(lisCCOWarningCaption, s, mtWarning, [mbIgnore,
           mbCancel], 0);
    @@ -1241,9 +1510,13 @@
       s:=FPCSrcDirComboBox.Text;
       if s<>'' then
         EnvironmentOptions.FPCSourceDirectory:=s;
    +  s:=MakeExeComboBox.Text;
    +  if s<>'' then
    +    EnvironmentOptions.MakeFilename:=s;
    +  s:=DebuggerComboBox.Text;
    +  if s<>'' then
    +    EnvironmentOptions.DebuggerFilename:=s;
     
    -  SetupMakeExe;
    -
       ModalResult:=mrOk;
     end;
     
    @@ -1267,6 +1540,12 @@
       end else if fCompilerFilenameChanged then begin
         UpdateFPCSrcDirCandidates;
         UpdateFPCSrcDirNote;
    +  end else if fMakeExeFilenameChanged then begin
    +    UpdateMakeExeCandidates;
    +    UpdateMakeExeNote;
    +  end else if fDebuggerFilenameChanged then begin
    +    UpdateDebuggerCandidates;
    +    UpdateDebuggerNote;
       end else
         IdleConnected:=false;
     end;
    @@ -1341,6 +1620,28 @@
       FillComboboxWithFileInfoList(FPCSrcDirComboBox,Dirs);
     end;
     
    +procedure TInitialSetupDialog.UpdateMakeExeCandidates;
    +var
    +  Files: TObjectList;
    +begin
    +  FLazarusDirChanged:=false;
    +  Files:=SearchMakeExeCandidates(false);
    +  FreeAndNil(FCandidates[sddtMakeExeFileName]);
    +  FCandidates[sddtMakeExeFileName]:=Files;
    +  FillComboboxWithFileInfoList(MakeExeComboBox,Files);
    +end;
    +
    +procedure TInitialSetupDialog.UpdateDebuggerCandidates;
    +var
    +  Files: TObjectList;
    +begin
    +  FLazarusDirChanged:=false;
    +  Files:=SearchDebuggerCandidates(false);
    +  FreeAndNil(FCandidates[sddtDebuggerFilename]);
    +  FCandidates[sddtDebuggerFilename]:=Files;
    +  FillComboboxWithFileInfoList(DebuggerComboBox,Files);
    +end;
    +
     procedure TInitialSetupDialog.FillComboboxWithFileInfoList(ABox: TComboBox;
       List: TObjectList; ItemIndex: integer);
     var
    @@ -1479,8 +1780,78 @@
       TVNodeFPCSources.SelectedIndex:=ImageIndex;
     end;
     
    -function TInitialSetupDialog.FirstErrorNode: TTreeNode;
    +procedure TInitialSetupDialog.UpdateMakeExeNote;
     var
    +  CurCaption: String;
    +  Note: string;
    +  Quality: TSDFilenameQuality;
    +  s: String;
    +  ImageIndex: Integer;
    +begin
    +  if csDestroying in ComponentState then exit;
    +  CurCaption:=MakeExeComboBox.Text;
    +  EnvironmentOptions.MakeFilename:=CurCaption;
    +  if fLastParsedMakeExe=EnvironmentOptions.GetParsedMakeFilename then exit;
    +  fLastParsedMakeExe:=EnvironmentOptions.GetParsedMakeFilename;
    +  //debugln(['TInitialSetupDialog.UpdateMakeExeNote ',fLastParsedMakeExe]);
    +  Quality:=CheckMakeExeQuality(fLastParsedMakeExe,Note);
    +
    +  case Quality of
    +  sddqInvalid: s:=lisError;
    +  sddqCompatible: s:='';
    +  else s:=lisWarning;
    +  end;
    +  if EnvironmentOptions.MakeFilename<>EnvironmentOptions.GetParsedMakeFilename
    +  then
    +    s:=lisFile2+EnvironmentOptions.GetParsedMakeFilename+LineEnding+
    +      LineEnding+s;
    +  MakeExeMemo.Text:=s+Note;
    +
    +  ImageIndex:=QualityToImgIndex(Quality);
    +  TVNodeMakeExe.ImageIndex:=ImageIndex;
    +  TVNodeMakeExe.SelectedIndex:=ImageIndex;
    +
    +  fMakeExeFilenameChanged:=true;
    +  IdleConnected:=true;
    +end;
    +
    +procedure TInitialSetupDialog.UpdateDebuggerNote;
    +var
    +  CurCaption: String;
    +  Note: string;
    +  Quality: TSDFilenameQuality;
    +  s: String;
    +  ImageIndex: Integer;
    +begin
    +  if csDestroying in ComponentState then exit;
    +  CurCaption:=DebuggerComboBox.Text;
    +  EnvironmentOptions.DebuggerFilename:=CurCaption;
    +  if fLastParsedDebugger=EnvironmentOptions.GetParsedDebuggerFilename then exit;
    +  fLastParsedDebugger:=EnvironmentOptions.GetParsedDebuggerFilename;
    +  //debugln(['TInitialSetupDialog.UpdateDebuggerNote ',fLastParsedDebugger]);
    +  Quality:=CheckDebuggerQuality(fLastParsedDebugger,Note);
    +
    +  case Quality of
    +  sddqInvalid: s:=lisError;
    +  sddqCompatible: s:='';
    +  else s:=lisWarning;
    +  end;
    +  if EnvironmentOptions.DebuggerFilename<>EnvironmentOptions.GetParsedDebuggerFilename
    +  then
    +    s:=lisFile2+EnvironmentOptions.GetParsedDebuggerFilename+LineEnding+
    +      LineEnding+s;
    +  DebuggerMemo.Text:=s+Note;
    +
    +  ImageIndex:=QualityToImgIndex(Quality);
    +  TVNodeDebugger.ImageIndex:=ImageIndex;
    +  TVNodeDebugger.SelectedIndex:=ImageIndex;
    +
    +  fDebuggerFilenameChanged:=true;
    +  IdleConnected:=true;
    +end;
    +
    +function TInitialSetupDialog.FirstErrorNode(IncludeWarnings: boolean): TTreeNode;
    +var
       i: Integer;
     begin
       for i:=0 to PropertiesTreeView.Items.TopLvlCount-1 do
    @@ -1488,6 +1859,14 @@
         Result:=PropertiesTreeView.Items.TopLvlItems[i];
         if Result.ImageIndex=ImgIDError then exit;
       end;
    +  if IncludeWarnings then
    +  begin
    +    for i:=0 to PropertiesTreeView.Items.TopLvlCount-1 do
    +    begin
    +      Result:=PropertiesTreeView.Items.TopLvlItems[i];
    +      if Result.ImageIndex=ImgIDWarning then exit;
    +    end;
    +  end;
       Result:=nil;
     end;
     
    @@ -1518,6 +1897,8 @@
         Result:=-1
       else if Quality=sddqWrongMinorVersion then
         Result:=ImgIDWarning
    +  else if Quality=sddqIncomplete then
    +    Result:=ImgIDWarning
       else
         Result:=ImgIDError;
     end;
    @@ -1568,9 +1949,38 @@
       fLastParsedFPCSrcDir:='. .';
       UpdateFPCSrcDirNote;
     
    -  // select first error
    -  Node:=FirstErrorNode;
    +  // Make executable
    +  UpdateMakeExeCandidates;
    +  if (not FileExistsCached(EnvironmentOptions.Filename)) then
    +  begin
    +    // first start => choose first best candidate
    +    Candidate:=GetFirstCandidate(FCandidates[sddtMakeExeFilename]);
    +    if Candidate<>nil then
    +      EnvironmentOptions.MakeFilename:=Candidate.Caption;
    +  end;
    +  MakeExeComboBox.Text:=EnvironmentOptions.MakeFilename;
    +  fLastParsedMakeExe:='. .';
    +  UpdateMakeExeNote;
    +
    +  // Debugger
    +  UpdateDebuggerCandidates;
    +  if (not FileExistsCached(EnvironmentOptions.Filename)) then
    +  begin
    +    // first start => choose first best candidate
    +    Candidate:=GetFirstCandidate(FCandidates[sddtDebuggerFilename]);
    +    if Candidate<>nil then
    +      EnvironmentOptions.DebuggerFilename:=Candidate.Caption;
    +  end;
    +  DebuggerComboBox.Text:=EnvironmentOptions.DebuggerFilename;
    +  fLastParsedDebugger:='. .';
    +  UpdateDebuggerNote;
    +
    +  // select first error...
    +  Node:=FirstErrorNode(false);
    +  // ... or warning if no errors found
       if Node=nil then
    +    Node:=FirstErrorNode(true);
    +  if Node=nil then
         Node:=TVNodeLazarus;
       PropertiesTreeView.Selected:=Node;
     end;
    Index: ide/lazarusidestrconsts.pas
    ===================================================================
    --- ide/lazarusidestrconsts.pas	(revision 38091)
    +++ ide/lazarusidestrconsts.pas	(working copy)
    @@ -2008,6 +2008,7 @@
       dlgCOLibraries = 'Libraries (-Fl):';
       dlgCODebugPath = 'Debugger path addition (none):';
       lisCompiler = 'Compiler';
    +  lisDebugger = 'Debugger';
       lisToFPCPath = 'Path:';
       lisCOSkipCallingCompiler = 'Skip calling compiler';
       lisCOAmbiguousAdditionalCompilerConfigFile = 'Ambiguous additional compiler '
    @@ -5437,6 +5438,10 @@
         +'Lazarus directory you will get a lot of warnings.';
       lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW = 'Without a proper '
         +'compiler the code browsing and compiling will be disappointing.';
    +  lisWithoutAProperDebuggerDebuggingWillBeDisappointing = 'Without a proper '
    +    +'debugger, debugging will be disappointing.';
    +  lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp = 'Without a proper '
    +    +'make executable the code browsing and compiling will be disappointing.';
       lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio = 'Without the proper '
         +'FPC sources code browsing and completion will be very limited.';
       lisTheLazarusDirectoryContainsTheSourcesOfTheIDEAndTh = 'The Lazarus '
    @@ -5446,6 +5451,11 @@
       lisTheFreePascalCompilerExecutableTypicallyHasTheName = 'The Free Pascal '
         +'compiler executable typically has the name "%s". You can also use the '
         +'target specific compiler like "%s". Please give the full file path.';
    +  lisTheMakeExecutableTypicallyHasTheName = 'The make executable typically '
    +    +'has the name "%s". Please give the full file path.';
    +  lisTheDebuggerExecutableTypicallyHasTheName = 'The debugger executable '
    +    +'typically has the name "%s". Pleae give the full file path. '
    +    +'A useful setting on Windows systems is: $(LazarusDir)\mingw\bin\$(TargetCPU)-$(TargetOS)\gdb.exe';
       lisFoundVersionExpected = 'Found version %s, expected %s';
       lisInvalidVersionIn = 'invalid version in %s';
       lisWrongVersionIn = 'wrong version in %s: %s';
    

Activities

2012-07-31 12:02

 

initial_checkdebugger.diff (34,233 bytes)
Index: ide/lazarusidestrconsts.pas
===================================================================
--- ide/lazarusidestrconsts.pas	(revision 38091)
+++ ide/lazarusidestrconsts.pas	(working copy)
@@ -2008,6 +2008,7 @@
   dlgCOLibraries = 'Libraries (-Fl):';
   dlgCODebugPath = 'Debugger path addition (none):';
   lisCompiler = 'Compiler';
+  lisDebugger = 'Debugger';
   lisToFPCPath = 'Path:';
   lisCOSkipCallingCompiler = 'Skip calling compiler';
   lisCOAmbiguousAdditionalCompilerConfigFile = 'Ambiguous additional compiler '
@@ -5437,6 +5438,10 @@
     +'Lazarus directory you will get a lot of warnings.';
   lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW = 'Without a proper '
     +'compiler the code browsing and compiling will be disappointing.';
+  lisWithoutAProperDebuggerDebuggingWillBeDisappointing = 'Without a proper '
+    +'debugger, debugging will be disappointing.';
+  lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp = 'Without a proper '
+    +'make executable the code browsing and compiling will be disappointing.';
   lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio = 'Without the proper '
     +'FPC sources code browsing and completion will be very limited.';
   lisTheLazarusDirectoryContainsTheSourcesOfTheIDEAndTh = 'The Lazarus '
@@ -5446,6 +5451,11 @@
   lisTheFreePascalCompilerExecutableTypicallyHasTheName = 'The Free Pascal '
     +'compiler executable typically has the name "%s". You can also use the '
     +'target specific compiler like "%s". Please give the full file path.';
+  lisTheMakeExecutableTypicallyHasTheName = 'The make executable typically '
+    +'has the name "%s". Please give the full file path.';
+  lisTheDebuggerExecutableTypicallyHasTheName = 'The debugger executable '
+    +'typically has the name "%s". Pleae give the full file path. '
+    +'A useful setting on Windows systems is: $(LazarusDir)\mingw\bin\$(TargetCPU)-$(TargetOS)\gdb.exe';
   lisFoundVersionExpected = 'Found version %s, expected %s';
   lisInvalidVersionIn = 'invalid version in %s';
   lisWrongVersionIn = 'wrong version in %s: %s';
Index: ide/initialsetupdlgs.lfm
===================================================================
--- ide/initialsetupdlgs.lfm	(revision 38091)
+++ ide/initialsetupdlgs.lfm	(working copy)
@@ -1,8 +1,8 @@
 object InitialSetupDialog: TInitialSetupDialog
   AnchorSideBottom.Side = asrBottom
-  Left = 253
+  Left = 319
   Height = 385
-  Top = 253
+  Top = 238
   Width = 620
   Caption = 'InitialSetupDialog'
   ClientHeight = 385
@@ -10,7 +10,7 @@
   OnCreate = FormCreate
   OnDestroy = FormDestroy
   Position = poScreenCenter
-  LCLVersion = '0.9.31'
+  LCLVersion = '1.1'
   object PropertiesTreeView: TTreeView
     AnchorSideLeft.Control = Owner
     AnchorSideTop.Control = WelcomePaintBox
@@ -18,7 +18,7 @@
     AnchorSideRight.Control = Splitter1
     AnchorSideBottom.Control = BtnPanel
     Left = 6
-    Height = 289
+    Height = 286
     Top = 54
     Width = 159
     Anchors = [akTop, akLeft, akRight, akBottom]
@@ -40,7 +40,7 @@
     AnchorSideBottom.Control = PropertiesTreeView
     AnchorSideBottom.Side = asrBottom
     Left = 165
-    Height = 289
+    Height = 286
     Top = 54
     Width = 5
     Align = alNone
@@ -48,21 +48,21 @@
   end
   object BtnPanel: TPanel
     Left = 10
-    Height = 22
-    Top = 353
+    Height = 25
+    Top = 350
     Width = 600
     Align = alBottom
     AutoSize = True
     BorderSpacing.Around = 10
     BevelOuter = bvNone
-    ClientHeight = 22
+    ClientHeight = 25
     ClientWidth = 600
     TabOrder = 2
     object StartIDEBitBtn: TBitBtn
-      Left = 489
-      Height = 22
+      Left = 500
+      Height = 25
       Top = 0
-      Width = 111
+      Width = 100
       Align = alRight
       AutoSize = True
       Caption = 'StartIDEBitBtn'
@@ -80,13 +80,13 @@
     AnchorSideBottom.Control = Splitter1
     AnchorSideBottom.Side = asrBottom
     Left = 170
-    Height = 289
+    Height = 286
     Top = 54
     Width = 444
-    ActivePage = FPCSourcesTabSheet
+    ActivePage = LazarusTabSheet
     Anchors = [akTop, akLeft, akRight, akBottom]
     BorderSpacing.Right = 6
-    TabIndex = 2
+    TabIndex = 0
     TabOrder = 3
     OnChange = PropertiesPageControlChange
     Options = [nboHidePageListPopup]
@@ -96,11 +96,11 @@
       ChildSizing.TopBottomSpacing = 6
       ChildSizing.HorizontalSpacing = 6
       ChildSizing.VerticalSpacing = 6
-      ClientHeight = 255
-      ClientWidth = 442
+      ClientHeight = 258
+      ClientWidth = 436
       object LazDirLabel: TLabel
         Left = 6
-        Height = 14
+        Height = 15
         Top = 6
         Width = 424
         Align = alTop
@@ -115,11 +115,11 @@
         AnchorSideRight.Control = LazarusTabSheet
         AnchorSideRight.Side = asrBottom
         Left = 6
-        Height = 21
-        Top = 26
+        Height = 23
+        Top = 27
         Width = 424
         Anchors = [akTop, akLeft, akRight]
-        ItemHeight = 0
+        ItemHeight = 15
         OnChange = LazDirComboBoxChange
         TabOrder = 0
         Text = 'LazDirComboBox'
@@ -128,8 +128,8 @@
         AnchorSideTop.Control = LazDirBrowseButton
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 174
-        Top = 82
+        Height = 165
+        Top = 87
         Width = 424
         Align = alBottom
         Anchors = [akTop, akLeft, akRight, akBottom]
@@ -148,9 +148,9 @@
         AnchorSideTop.Side = asrBottom
         AnchorSideRight.Side = asrBottom
         Left = 6
-        Height = 23
-        Top = 53
-        Width = 122
+        Height = 25
+        Top = 56
+        Width = 132
         AutoSize = True
         Caption = 'LazDirBrowseButton'
         OnClick = LazDirBrowseButtonClick
@@ -163,13 +163,13 @@
       ChildSizing.TopBottomSpacing = 6
       ChildSizing.HorizontalSpacing = 6
       ChildSizing.VerticalSpacing = 6
-      ClientHeight = 250
-      ClientWidth = 438
+      ClientHeight = 258
+      ClientWidth = 436
       object CompilerLabel: TLabel
         Left = 6
-        Height = 17
+        Height = 15
         Top = 6
-        Width = 426
+        Width = 424
         Align = alTop
         Caption = 'CompilerLabel'
         ParentColor = False
@@ -182,11 +182,11 @@
         AnchorSideRight.Control = CompilerTabSheet
         AnchorSideRight.Side = asrBottom
         Left = 6
-        Height = 21
-        Top = 29
-        Width = 426
+        Height = 23
+        Top = 27
+        Width = 424
         Anchors = [akTop, akLeft, akRight]
-        ItemHeight = 0
+        ItemHeight = 15
         OnChange = CompilerComboBoxChange
         TabOrder = 0
         Text = 'CompilerComboBox'
@@ -196,9 +196,9 @@
         AnchorSideTop.Control = CompilerComboBox
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 20
+        Height = 25
         Top = 56
-        Width = 168
+        Width = 149
         AutoSize = True
         Caption = 'CompilerBrowseButton'
         OnClick = CompilerBrowseButtonClick
@@ -213,9 +213,9 @@
         AnchorSideBottom.Control = CompilerTabSheet
         AnchorSideBottom.Side = asrBottom
         Left = 6
-        Height = 162
-        Top = 82
-        Width = 426
+        Height = 165
+        Top = 87
+        Width = 424
         Anchors = [akTop, akLeft, akRight, akBottom]
         Lines.Strings = (
           'CompilerMemo'
@@ -232,13 +232,13 @@
       ChildSizing.TopBottomSpacing = 6
       ChildSizing.HorizontalSpacing = 6
       ChildSizing.VerticalSpacing = 6
-      ClientHeight = 250
-      ClientWidth = 438
+      ClientHeight = 258
+      ClientWidth = 436
       object FPCSrcDirLabel: TLabel
         Left = 6
-        Height = 17
+        Height = 15
         Top = 6
-        Width = 426
+        Width = 424
         Align = alTop
         Caption = 'FPCSrcDirLabel'
         ParentColor = False
@@ -246,11 +246,11 @@
       end
       object FPCSrcDirComboBox: TComboBox
         Left = 6
-        Height = 21
-        Top = 29
-        Width = 426
+        Height = 23
+        Top = 27
+        Width = 424
         Align = alTop
-        ItemHeight = 0
+        ItemHeight = 15
         OnChange = FPCSrcDirComboBoxChange
         TabOrder = 0
         Text = 'FPCSrcDirComboBox'
@@ -260,9 +260,9 @@
         AnchorSideTop.Control = FPCSrcDirComboBox
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 20
+        Height = 25
         Top = 56
-        Width = 171
+        Width = 152
         AutoSize = True
         Caption = 'FPCSrcDirBrowseButton'
         OnClick = FPCSrcDirBrowseButtonClick
@@ -272,9 +272,9 @@
         AnchorSideTop.Control = FPCSrcDirBrowseButton
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 162
-        Top = 82
-        Width = 426
+        Height = 165
+        Top = 87
+        Width = 424
         Align = alBottom
         Anchors = [akTop, akLeft, akRight, akBottom]
         Lines.Strings = (
@@ -286,6 +286,118 @@
         TabOrder = 2
       end
     end
+    object MakeExeTabSheet: TTabSheet
+      Caption = 'MakeExeTabSheet'
+      ClientHeight = 258
+      ClientWidth = 436
+      object MakeExeComboBox: TComboBox
+        Left = 0
+        Height = 23
+        Top = 15
+        Width = 436
+        Align = alTop
+        ItemHeight = 15
+        OnChange = MakeExeComboBoxChange
+        TabOrder = 0
+        Text = 'MakeExeComboBox'
+      end
+      object MakeExeLabel: TLabel
+        Left = 0
+        Height = 15
+        Top = 0
+        Width = 436
+        Align = alTop
+        Caption = 'MakeExeLabel'
+        ParentColor = False
+        WordWrap = True
+      end
+      object MakeExeBrowseButton: TButton
+        AnchorSideLeft.Control = FPCSourcesTabSheet
+        AnchorSideTop.Control = MakeExeComboBox
+        AnchorSideTop.Side = asrBottom
+        Left = 6
+        Height = 25
+        Top = 38
+        Width = 146
+        AutoSize = True
+        Caption = 'MakeExeBrowseButton'
+        OnClick = MakeExeBrowseButtonClick
+        TabOrder = 1
+      end
+      object MakeExeMemo: TMemo
+        AnchorSideTop.Control = MakeExeBrowseButton
+        AnchorSideTop.Side = asrBottom
+        Left = 0
+        Height = 195
+        Top = 63
+        Width = 436
+        Align = alBottom
+        Anchors = [akTop, akLeft, akRight, akBottom]
+        Lines.Strings = (
+          'FPCSrcDirMemo'
+          ''
+          ''
+        )
+        ReadOnly = True
+        TabOrder = 2
+      end
+    end
+    object DebuggerTabSheet: TTabSheet
+      Caption = 'DebuggerTabSheet'
+      ClientHeight = 258
+      ClientWidth = 436
+      object DebuggerComboBox: TComboBox
+        Left = 0
+        Height = 23
+        Top = 15
+        Width = 436
+        Align = alTop
+        ItemHeight = 15
+        OnChange = DebuggerComboBoxChange
+        TabOrder = 0
+        Text = 'DebuggerComboBox'
+      end
+      object DebuggerLabel: TLabel
+        Left = 0
+        Height = 15
+        Top = 0
+        Width = 436
+        Align = alTop
+        Caption = 'DebuggerLabel'
+        ParentColor = False
+        WordWrap = True
+      end
+      object DebuggerBrowseButton: TButton
+        AnchorSideLeft.Control = FPCSourcesTabSheet
+        AnchorSideTop.Control = DebuggerComboBox
+        AnchorSideTop.Side = asrBottom
+        Left = 6
+        Height = 25
+        Top = 38
+        Width = 152
+        AutoSize = True
+        Caption = 'DebuggerBrowseButton'
+        OnClick = DebuggerBrowseButtonClick
+        TabOrder = 1
+      end
+      object DebuggerMemo: TMemo
+        AnchorSideTop.Control = DebuggerBrowseButton
+        AnchorSideTop.Side = asrBottom
+        Left = 0
+        Height = 195
+        Top = 63
+        Width = 436
+        Align = alBottom
+        Anchors = [akTop, akLeft, akRight, akBottom]
+        Lines.Strings = (
+          'FPCSrcDirMemo'
+          ''
+          ''
+        )
+        ReadOnly = True
+        TabOrder = 2
+      end
+    end
   end
   object WelcomePaintBox: TPaintBox
     Left = 0
Index: ide/initialsetupdlgs.pas
===================================================================
--- ide/initialsetupdlgs.pas	(revision 38091)
+++ ide/initialsetupdlgs.pas	(working copy)
@@ -67,7 +67,9 @@
   TSDFilenameType = (
     sddtLazarusSrcDir,
     sddtCompilerFilename,
-    sddtFPCSrcDir
+    sddtFPCSrcDir,
+    sddtMakeExeFilename,
+    sddtDebuggerFilename
     );
 
   { TInitialSetupDialog }
@@ -79,9 +81,17 @@
     CompilerLabel: TLabel;
     CompilerMemo: TMemo;
     FPCSrcDirBrowseButton: TButton;
+    MakeExeBrowseButton: TButton;
+    DebuggerBrowseButton: TButton;
     FPCSrcDirComboBox: TComboBox;
+    MakeExeComboBox: TComboBox;
+    DebuggerComboBox: TComboBox;
     FPCSrcDirLabel: TLabel;
+    MakeExeLabel: TLabel;
+    DebuggerLabel: TLabel;
     FPCSrcDirMemo: TMemo;
+    MakeExeMemo: TMemo;
+    DebuggerMemo: TMemo;
     ImageList1: TImageList;
     LazDirBrowseButton: TButton;
     LazDirLabel: TLabel;
@@ -94,15 +104,21 @@
     LazarusTabSheet: TTabSheet;
     CompilerTabSheet: TTabSheet;
     FPCSourcesTabSheet: TTabSheet;
+    MakeExeTabSheet: TTabSheet;
+    DebuggerTabSheet: TTabSheet;
     WelcomePaintBox: TPaintBox;
     procedure CompilerBrowseButtonClick(Sender: TObject);
     procedure CompilerComboBoxChange(Sender: TObject);
+    procedure DebuggerBrowseButtonClick(Sender: TObject);
+    procedure DebuggerComboBoxChange(Sender: TObject);
     procedure FormCreate(Sender: TObject);
     procedure FormDestroy(Sender: TObject);
     procedure FPCSrcDirBrowseButtonClick(Sender: TObject);
     procedure FPCSrcDirComboBoxChange(Sender: TObject);
     procedure LazDirBrowseButtonClick(Sender: TObject);
     procedure LazDirComboBoxChange(Sender: TObject);
+    procedure MakeExeBrowseButtonClick(Sender: TObject);
+    procedure MakeExeComboBoxChange(Sender: TObject);
     procedure PropertiesPageControlChange(Sender: TObject);
     procedure PropertiesTreeViewSelectionChanged(Sender: TObject);
     procedure StartIDEBitBtnClick(Sender: TObject);
@@ -111,9 +127,13 @@
   private
     FLazarusDirChanged: boolean;
     fCompilerFilenameChanged: boolean;
+    fMakeExeFilenameChanged: boolean;
+    fDebuggerFilenameChanged: boolean;
     FLastParsedLazDir: string;
     fLastParsedCompiler: string;
     fLastParsedFPCSrcDir: string;
+    fLastParsedMakeExe: string;
+    fLastParsedDebugger: string;
     FIdleConnected: boolean;
     ImgIDError: LongInt;
     ImgIDWarning: LongInt;
@@ -125,12 +145,16 @@
     procedure UpdateLazarusDirCandidates;
     procedure UpdateCompilerFilenameCandidates;
     procedure UpdateFPCSrcDirCandidates;
+    procedure UpdateMakeExeCandidates;
+    procedure UpdateDebuggerCandidates;
     procedure FillComboboxWithFileInfoList(ABox: TComboBox; List: TObjectList;
        ItemIndex: integer = 0);
     procedure SetIdleConnected(const AValue: boolean);
     procedure UpdateLazDirNote;
     procedure UpdateCompilerNote;
     procedure UpdateFPCSrcDirNote;
+    procedure UpdateMakeExeNote;
+    procedure UpdateDebuggerNote;
     function FirstErrorNode: TTreeNode;
     function GetFPCVer: string;
     function GetFirstCandidate(Candidates: TObjectList;
@@ -140,7 +164,9 @@
     TVNodeLazarus: TTreeNode;
     TVNodeCompiler: TTreeNode;
     TVNodeFPCSources: TTreeNode;
-    procedure Init;
+    TVNodeMakeExe: TTreeNode;
+    TVNodeDebugger: TTreeNode;
+    procedure Init; //Check for config errors, find and show alternatives
     property IdleConnected: boolean read FIdleConnected write SetIdleConnected;
   end;
 
@@ -164,10 +190,15 @@
 procedure SetupFPCSrcDir(FPCVer: string);
 
 function CheckMakeExeQuality(AFilename: string;
-  out Note: string): TSDFilenameQuality;
-function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList;
-procedure SetupMakeExe;
+  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid make executable
+function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList; //Search make candidates and add them to the list, including quality level
+procedure SetupMakeExe; //Checks if the make specified in user's options (if any) is ok. If not, search for and set a valid one if possible
 
+function CheckDebuggerQuality(AFilename: string;
+  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid debugger (only gdb supported for now)
+function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList; //Search debugger candidates and add them to list, including quality level
+procedure SetupDebugger; //Checks if the debugger specified in user's option (if any) is ok. If not, search for and set a valid one if possible
+
 function GetValueFromPrimaryConfig(OptionFilename, Path: string): string;
 function GetValueFromSecondaryConfig(OptionFilename, Path: string): string;
 function GetValueFromIDEConfig(OptionFilename, Path: string): string;
@@ -565,7 +596,7 @@
 
     // check $(LazarusDir)\fpc\bin\i386-win32\fpc.exe
     if CheckFile(SetDirSeparators('$(LazarusDir)/fpc/bin/$(TargetCPU)-$(TargetOS)/')+ShortCompFile,Result)
-    then exit;
+      then exit;
 
     // check common directories
     Files:=TStringList.Create;
@@ -577,8 +608,8 @@
       Files.Free;
     end;
 
+    // Windows-only locations:
     if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
-      // Windows has some special places
       SysDrive:=GetEnvironmentVariableUTF8('SYSTEMDRIVE');
       if SysDrive='' then SysDrive:='C:';
       SysDrive:=AppendPathDelim(SysDrive);
@@ -842,6 +873,165 @@
   end;
 end;
 
+function CheckDebuggerQuality(AFilename: string; out Note: string
+  ): TSDFilenameQuality;
+begin
+  Result:=sddqInvalid;
+  AFilename:=TrimFilename(AFilename);
+  if not FileExistsCached(AFilename) then
+  begin
+    Note:=lisFileNotFound4;
+    exit;
+  end;
+  if DirPathExistsCached(AFilename) then
+  begin
+    Note:=lisFileIsDirectory;
+    exit;
+  end;
+  if not FileIsExecutableCached(AFilename) then
+  begin
+    Note:=lisFileIsNotAnExecutable;
+    exit;
+  end;
+
+  { We could call gdb and parse the output looking for something like
+  GNU gdb, but that may be going too far. }
+  Note:=lisOk;
+  Result:=sddqCompatible;
+end;
+
+function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList;
+
+  function CheckFile(AFilename: string; var List: TObjectList): boolean;
+  var
+    Item: TSDFileInfo;
+    RealFilename: String;
+  begin
+    Result:=false;
+    if AFilename='' then exit;
+    DoDirSeparators(AFilename);
+    // check if already checked
+    if CaptionInSDFileList(AFilename,List) then exit;
+    EnvironmentOptions.DebuggerFilename:=AFilename;
+    RealFilename:=EnvironmentOptions.GetParsedDebuggerFilename;
+    debugln(['SearchDebuggerCandidates Value=',AFilename,' File=',RealFilename]);
+    if RealFilename='' then exit;
+    // check if exists
+    if not FileExistsCached(RealFilename) then exit;
+    // add to list and check quality
+    Item:=TSDFileInfo.Create;
+    Item.Filename:=RealFilename;
+    Item.Quality:=CheckDebuggerQuality(RealFilename,Item.Note);
+    Item.Caption:=AFilename;
+    if List=nil then
+      List:=TObjectList.create(true);
+    List.Add(Item);
+    Result:=(Item.Quality=sddqCompatible) and StopIfFits;
+  end;
+const
+  DebuggerFileName='gdb'; //For Windows, .exe will be appended
+var
+  OldDebuggerFilename: String;
+  AFilename: String;
+  Files: TStringList;
+  i: Integer;
+begin
+  Result:=nil;
+
+  OldDebuggerFilename:=EnvironmentOptions.DebuggerFilename;
+  try
+    // check current setting
+    if CheckFile(EnvironmentOptions.DebuggerFilename,Result) then exit;
+
+    // check the primary options
+    AFilename:=GetValueFromPrimaryConfig(EnvOptsConfFileName,
+                                    'EnvironmentOptions/DebuggerFilename/Value');
+    if CheckFile(AFilename,Result) then exit;
+
+    // check the secondary options
+    AFilename:=GetValueFromSecondaryConfig(EnvOptsConfFileName,
+                                    'EnvironmentOptions/DebuggerFilename/Value');
+    if CheckFile(AFilename,Result) then exit;
+
+    // The next 2 locations are locations used by older and newer versions of the Windows installers
+    // If other platform installers follow the same strategy, this can be useful.
+    // Chances of this are low (gdb is generally installed in the path on Unixy systems), but it can't hurt...
+    // and it can be useful for cross compiling/custom setups.
+
+    // Check new installation location: $(LazarusDir)\mingw\$(TargetCPU)-$(TargetOS)\bin\gdb.exe
+    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/$(TargetCPU)-$(TargetOS)/bin/'+DebuggerFileName+GetExecutableExt),Result)
+      then exit;
+
+    // Older Lazarus installers did not use macros for their debuggers: there was only one debugger
+    // Check old installation location: $(LazarusDir)\mingw\bin\gdb.exe
+    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/bin/'+DebuggerFileName+GetExecutableExt),Result)
+      then exit;
+
+    // Windows-only locations:
+    if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
+      // check for debugger in fpc.exe directory - could be a lucky shot
+      if CheckFile(SetDirSeparators('$Path($(CompPath))/'+DebuggerFileName+GetExecutableExt),Result)
+        then exit;
+    end;
+
+    // check history
+    Files:=EnvironmentOptions.DebuggerFileHistory;
+    if Files<>nil then
+      for i:=0 to Files.Count-1 do
+        if CheckFile(Files[i],Result) then exit;
+
+    // check PATH
+    AFilename:=DebuggerFileName;
+    AFilename+=GetExecutableExt;
+    if CheckFile(FindDefaultExecutablePath(AFilename),Result) then exit;
+
+    // There are no common directories apart from the PATH
+    // where gdb would be installed. Otherwise we could do something similar as
+    // in SearchMakeExeCandidates.
+  finally
+    EnvironmentOptions.DebuggerFilename:=OldDebuggerFilename;
+  end;
+end;
+
+procedure SetupDebugger;
+var
+  Note: string;
+  Filename: String;
+  Quality: TSDFilenameQuality;
+  BestDir: TSDFileInfo;
+  List: TObjectList;
+begin
+  Filename:=EnvironmentOptions.GetParsedDebuggerFilename;
+  Quality:=CheckDebuggerQuality(Filename,Note);
+  if Quality<>sddqInvalid then exit;
+  // bad debugger
+  dbgout('SetupDebugger:');
+  if EnvironmentOptions.DebuggerFilename<>'' then
+  begin
+    dbgout(' The "gdb" executable "',EnvironmentOptions.DebuggerFilename,'"');
+    if EnvironmentOptions.DebuggerFilename<>Filename then
+      dbgout(' => "',Filename,'"');
+    dbgout(' is invalid (Error: ',Note,')');
+    debugln(' Searching a proper one ...');
+  end else begin
+    debugln(' Searching "gdb" ...');
+  end;
+  List:=SearchDebuggerCandidates(true);
+  try
+    BestDir:=nil;
+    if List<>nil then
+      BestDir:=TSDFileInfo(List[List.Count-1]);
+    if (BestDir=nil) or (BestDir.Quality=sddqInvalid) then begin
+      debugln(['SetupDebugger: no proper "gdb" found.']);
+      exit;
+    end;
+    EnvironmentOptions.DebuggerFilename:=BestDir.Filename;
+    debugln(['SetupDebugger: using ',EnvironmentOptions.DebuggerFilename]);
+  finally
+    List.Free;
+  end;
+end;
+
 function CheckMakeExeQuality(AFilename: string; out Note: string
   ): TSDFilenameQuality;
 begin
@@ -863,11 +1053,13 @@
     exit;
   end;
 
+  // Windows-only locations:
   if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
-    // under Windows the make.exe is in the same directory as fpc.exe
+    // under Windows, make.exe is in the same directory as fpc.exe
     if not FileExistsCached(ExtractFilePath(AFilename)+'fpc.exe') then begin
-      Note:='There is no fpc.exe in the directory of the '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the fpc compiler.';
+      Note:='There is no fpc.exe in the directory of '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the FPC compiler.';
       Result:=sddqIncomplete;
+      exit;
     end;
   end;
 
@@ -926,6 +1118,7 @@
                                     'EnvironmentOptions/MakeFilename/Value');
     if CheckFile(AFilename,Result) then exit;
 
+    // Windows-only locations:
     if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
       // check make in fpc.exe directory
       if CheckFile(SetDirSeparators('$Path($(CompPath))/make.exe'),Result)
@@ -1098,6 +1291,8 @@
   LazarusTabSheet.Caption:='Lazarus';
   CompilerTabSheet.Caption:=lisCompiler;
   FPCSourcesTabSheet.Caption:=lisFPCSources;
+  MakeExeTabSheet.Caption:='make';
+  DebuggerTabSheet.Caption:=lisDebugger;
 
   FHeadGraphic:=TPortableNetworkGraphic.Create;
   FHeadGraphic.LoadFromLazarusResource('ide_icon48x48');
@@ -1105,6 +1300,8 @@
   TVNodeLazarus:=PropertiesTreeView.Items.Add(nil,LazarusTabSheet.Caption);
   TVNodeCompiler:=PropertiesTreeView.Items.Add(nil,CompilerTabSheet.Caption);
   TVNodeFPCSources:=PropertiesTreeView.Items.Add(nil,FPCSourcesTabSheet.Caption);
+  TVNodeMakeExe:=PropertiesTreeView.Items.Add(nil,MakeExeTabSheet.Caption);
+  TVNodeDebugger:=PropertiesTreeView.Items.Add(nil,DebuggerTabSheet.Caption);
   ImgIDError := ImageList1.AddLazarusResource('state_error');
   ImgIDWarning := ImageList1.AddLazarusResource('state_warning');
 
@@ -1122,6 +1319,15 @@
   FPCSrcDirLabel.Caption:=Format(
     lisTheSourcesOfTheFreePascalPackagesAreRequiredForBro, [SetDirSeparators('rtl'
     +'/linux/system.pp')]);
+
+  MakeExeBrowseButton.Caption:=lisPathEditBrowse;
+  MakeExeLabel.Caption:=Format(
+    lisTheMakeExecutableTypicallyHasTheName, ['make'+GetExecutableExt('')]);
+
+  DebuggerBrowseButton.Caption:=lisPathEditBrowse;
+  DebuggerLabel.Caption:=Format(
+    lisTheDebuggerExecutableTypicallyHasTheName, ['gdb'+GetExecutableExt('')]);
+
 end;
 
 procedure TInitialSetupDialog.CompilerComboBoxChange(Sender: TObject);
@@ -1129,6 +1335,35 @@
   UpdateCompilerNote;
 end;
 
+procedure TInitialSetupDialog.DebuggerBrowseButtonClick(Sender: TObject);
+var
+  Filename: String;
+  Dlg: TOpenDialog;
+  Filter: String;
+begin
+  Dlg:=TOpenDialog.Create(nil);
+  try
+    Filename:='gdb'+GetExecutableExt;
+    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
+    Dlg.Options:=Dlg.Options+[ofFileMustExist];
+    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
+    if ExtractFileExt(Filename)<>'' then
+      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
+    Dlg.Filter:=Filter;
+    if not Dlg.Execute then exit;
+    Filename:=Dlg.FileName;
+  finally
+    Dlg.Free;
+  end;
+  DebuggerComboBox.Text:=Filename;
+  UpdateDebuggerNote;
+end;
+
+procedure TInitialSetupDialog.DebuggerComboBoxChange(Sender: TObject);
+begin
+  UpdateDebuggerNote;
+end;
+
 procedure TInitialSetupDialog.CompilerBrowseButtonClick(Sender: TObject);
 var
   Filename: String;
@@ -1193,6 +1428,35 @@
   UpdateLazDirNote;
 end;
 
+procedure TInitialSetupDialog.MakeExeBrowseButtonClick(Sender: TObject);
+var
+  Filename: String;
+  Dlg: TOpenDialog;
+  Filter: String;
+begin
+  Dlg:=TOpenDialog.Create(nil);
+  try
+    Filename:='make'+GetExecutableExt;
+    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
+    Dlg.Options:=Dlg.Options+[ofFileMustExist];
+    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
+    if ExtractFileExt(Filename)<>'' then
+      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
+    Dlg.Filter:=Filter;
+    if not Dlg.Execute then exit;
+    Filename:=Dlg.FileName;
+  finally
+    Dlg.Free;
+  end;
+  MakeExeComboBox.Text:=Filename;
+  UpdateMakeExeNote;
+end;
+
+procedure TInitialSetupDialog.MakeExeComboBoxChange(Sender: TObject);
+begin
+  UpdateMakeExeNote;
+end;
+
 procedure TInitialSetupDialog.PropertiesPageControlChange(Sender: TObject);
 var
   s: String;
@@ -1225,7 +1489,11 @@
   else if Node=TVNodeCompiler then
     s:=lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW
   else if Node=TVNodeFPCSources then
-    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio;
+    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio
+  else if Node=TVNodeMakeExe then
+    s:=lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp
+  else if Node=TVNodeDebugger then
+    s:=lisWithoutAProperDebuggerDebuggingWillBeDisappointing;
   if s<>'' then begin
     MsgResult:=MessageDlg(lisCCOWarningCaption, s, mtWarning, [mbIgnore,
       mbCancel], 0);
@@ -1241,9 +1509,13 @@
   s:=FPCSrcDirComboBox.Text;
   if s<>'' then
     EnvironmentOptions.FPCSourceDirectory:=s;
+  s:=MakeExeComboBox.Text;
+  if s<>'' then
+    EnvironmentOptions.MakeFilename:=s;
+  s:=DebuggerComboBox.Text;
+  if s<>'' then
+    EnvironmentOptions.DebuggerFilename:=s;
 
-  SetupMakeExe;
-
   ModalResult:=mrOk;
 end;
 
@@ -1267,6 +1539,12 @@
   end else if fCompilerFilenameChanged then begin
     UpdateFPCSrcDirCandidates;
     UpdateFPCSrcDirNote;
+  end else if fMakeExeFilenameChanged then begin
+    UpdateMakeExeCandidates;
+    UpdateMakeExeNote;
+  end else if fDebuggerFilenameChanged then begin
+    UpdateDebuggerCandidates;
+    UpdateDebuggerNote;
   end else
     IdleConnected:=false;
 end;
@@ -1341,6 +1619,28 @@
   FillComboboxWithFileInfoList(FPCSrcDirComboBox,Dirs);
 end;
 
+procedure TInitialSetupDialog.UpdateMakeExeCandidates;
+var
+  Files: TObjectList;
+begin
+  FLazarusDirChanged:=false;
+  Files:=SearchMakeExeCandidates(false);
+  FreeAndNil(FCandidates[sddtMakeExeFileName]);
+  FCandidates[sddtMakeExeFileName]:=Files;
+  FillComboboxWithFileInfoList(MakeExeComboBox,Files);
+end;
+
+procedure TInitialSetupDialog.UpdateDebuggerCandidates;
+var
+  Files: TObjectList;
+begin
+  FLazarusDirChanged:=false;
+  Files:=SearchDebuggerCandidates(false);
+  FreeAndNil(FCandidates[sddtDebuggerFilename]);
+  FCandidates[sddtDebuggerFilename]:=Files;
+  FillComboboxWithFileInfoList(DebuggerComboBox,Files);
+end;
+
 procedure TInitialSetupDialog.FillComboboxWithFileInfoList(ABox: TComboBox;
   List: TObjectList; ItemIndex: integer);
 var
@@ -1479,6 +1779,76 @@
   TVNodeFPCSources.SelectedIndex:=ImageIndex;
 end;
 
+procedure TInitialSetupDialog.UpdateMakeExeNote;
+var
+  CurCaption: String;
+  Note: string;
+  Quality: TSDFilenameQuality;
+  s: String;
+  ImageIndex: Integer;
+begin
+  if csDestroying in ComponentState then exit;
+  CurCaption:=MakeExeComboBox.Text;
+  EnvironmentOptions.MakeFilename:=CurCaption;
+  if fLastParsedMakeExe=EnvironmentOptions.GetParsedMakeFilename then exit;
+  fLastParsedMakeExe:=EnvironmentOptions.GetParsedMakeFilename;
+  //debugln(['TInitialSetupDialog.UpdateMakeExeNote ',fLastParsedMakeExe]);
+  Quality:=CheckMakeExeQuality(fLastParsedMakeExe,Note);
+
+  case Quality of
+  sddqInvalid: s:=lisError;
+  sddqCompatible: s:='';
+  else s:=lisWarning;
+  end;
+  if EnvironmentOptions.MakeFilename<>EnvironmentOptions.GetParsedMakeFilename
+  then
+    s:=lisFile2+EnvironmentOptions.GetParsedMakeFilename+LineEnding+
+      LineEnding+s;
+  MakeExeMemo.Text:=s+Note;
+
+  ImageIndex:=QualityToImgIndex(Quality);
+  TVNodeMakeExe.ImageIndex:=ImageIndex;
+  TVNodeMakeExe.SelectedIndex:=ImageIndex;
+
+  fMakeExeFilenameChanged:=true;
+  IdleConnected:=true;
+end;
+
+procedure TInitialSetupDialog.UpdateDebuggerNote;
+var
+  CurCaption: String;
+  Note: string;
+  Quality: TSDFilenameQuality;
+  s: String;
+  ImageIndex: Integer;
+begin
+  if csDestroying in ComponentState then exit;
+  CurCaption:=DebuggerComboBox.Text;
+  EnvironmentOptions.DebuggerFilename:=CurCaption;
+  if fLastParsedDebugger=EnvironmentOptions.GetParsedDebuggerFilename then exit;
+  fLastParsedDebugger:=EnvironmentOptions.GetParsedDebuggerFilename;
+  //debugln(['TInitialSetupDialog.UpdateDebuggerNote ',fLastParsedDebugger]);
+  Quality:=CheckDebuggerQuality(fLastParsedDebugger,Note);
+
+  case Quality of
+  sddqInvalid: s:=lisError;
+  sddqCompatible: s:='';
+  else s:=lisWarning;
+  end;
+  if EnvironmentOptions.DebuggerFilename<>EnvironmentOptions.GetParsedDebuggerFilename
+  then
+    s:=lisFile2+EnvironmentOptions.GetParsedDebuggerFilename+LineEnding+
+      LineEnding+s;
+  DebuggerMemo.Text:=s+Note;
+
+  ImageIndex:=QualityToImgIndex(Quality);
+  TVNodeDebugger.ImageIndex:=ImageIndex;
+  TVNodeDebugger.SelectedIndex:=ImageIndex;
+
+  fDebuggerFilenameChanged:=true;
+  IdleConnected:=true;
+end;
+
 function TInitialSetupDialog.FirstErrorNode: TTreeNode;
 var
   i: Integer;
@@ -1518,6 +1888,8 @@
     Result:=-1
   else if Quality=sddqWrongMinorVersion then
     Result:=ImgIDWarning
+  else if Quality=sddqIncomplete then
+    Result:=ImgIDWarning
   else
     Result:=ImgIDError;
 end;
@@ -1568,6 +1940,32 @@
   fLastParsedFPCSrcDir:='. .';
   UpdateFPCSrcDirNote;
 
+  // Make executable
+  UpdateMakeExeCandidates;
+  if (not FileExistsCached(EnvironmentOptions.Filename)) then
+  begin
+    // first start => choose first best candidate
+    Candidate:=GetFirstCandidate(FCandidates[sddtMakeExeFilename]);
+    if Candidate<>nil then
+      EnvironmentOptions.MakeFilename:=Candidate.Caption;
+  end;
+  MakeExeComboBox.Text:=EnvironmentOptions.MakeFilename;
+  fLastParsedMakeExe:='. .';
+  UpdateMakeExeNote;
+
+  // Debugger
+  UpdateDebuggerCandidates;
+  if (not FileExistsCached(EnvironmentOptions.Filename)) then
+  begin
+    // first start => choose first best candidate
+    Candidate:=GetFirstCandidate(FCandidates[sddtDebuggerFilename]);
+    if Candidate<>nil then
+      EnvironmentOptions.DebuggerFilename:=Candidate.Caption;
+  end;
+  DebuggerComboBox.Text:=EnvironmentOptions.DebuggerFilename;
+  fLastParsedDebugger:='. .';
+  UpdateDebuggerNote;
+
   // select first error
   Node:=FirstErrorNode;
   if Node=nil then
Index: tools/install/win/environmentoptions.xml
===================================================================
--- tools/install/win/environmentoptions.xml	(revision 38091)
+++ tools/install/win/environmentoptions.xml	(working copy)
@@ -13,7 +13,7 @@
     <TestBuildDirectory Value="%Temp%">
     </TestBuildDirectory>
     <Debugger Class="TGDBMIDebugger"/>
-    <DebuggerFilename Value="%LazDir%\mingw\bin\gdb.exe">
+    <DebuggerFilename Value="%LazDir%\mingw\$(TargetCPU)-$(TargetOS)\bin\gdb.exe">
     </DebuggerFilename>
   </EnvironmentOptions>
 </CONFIG>

Reinier Olislagers

2012-07-31 12:11

developer   ~0061315

Oops, patch contained another patch. Please use the second file.

2012-07-31 12:12

 

initial_checkdebugger2.diff (33,660 bytes)
Index: ide/initialsetupdlgs.lfm
===================================================================
--- ide/initialsetupdlgs.lfm	(revision 38091)
+++ ide/initialsetupdlgs.lfm	(working copy)
@@ -1,8 +1,8 @@
 object InitialSetupDialog: TInitialSetupDialog
   AnchorSideBottom.Side = asrBottom
-  Left = 253
+  Left = 319
   Height = 385
-  Top = 253
+  Top = 238
   Width = 620
   Caption = 'InitialSetupDialog'
   ClientHeight = 385
@@ -10,7 +10,7 @@
   OnCreate = FormCreate
   OnDestroy = FormDestroy
   Position = poScreenCenter
-  LCLVersion = '0.9.31'
+  LCLVersion = '1.1'
   object PropertiesTreeView: TTreeView
     AnchorSideLeft.Control = Owner
     AnchorSideTop.Control = WelcomePaintBox
@@ -18,7 +18,7 @@
     AnchorSideRight.Control = Splitter1
     AnchorSideBottom.Control = BtnPanel
     Left = 6
-    Height = 289
+    Height = 286
     Top = 54
     Width = 159
     Anchors = [akTop, akLeft, akRight, akBottom]
@@ -40,7 +40,7 @@
     AnchorSideBottom.Control = PropertiesTreeView
     AnchorSideBottom.Side = asrBottom
     Left = 165
-    Height = 289
+    Height = 286
     Top = 54
     Width = 5
     Align = alNone
@@ -48,21 +48,21 @@
   end
   object BtnPanel: TPanel
     Left = 10
-    Height = 22
-    Top = 353
+    Height = 25
+    Top = 350
     Width = 600
     Align = alBottom
     AutoSize = True
     BorderSpacing.Around = 10
     BevelOuter = bvNone
-    ClientHeight = 22
+    ClientHeight = 25
     ClientWidth = 600
     TabOrder = 2
     object StartIDEBitBtn: TBitBtn
-      Left = 489
-      Height = 22
+      Left = 500
+      Height = 25
       Top = 0
-      Width = 111
+      Width = 100
       Align = alRight
       AutoSize = True
       Caption = 'StartIDEBitBtn'
@@ -80,13 +80,13 @@
     AnchorSideBottom.Control = Splitter1
     AnchorSideBottom.Side = asrBottom
     Left = 170
-    Height = 289
+    Height = 286
     Top = 54
     Width = 444
-    ActivePage = FPCSourcesTabSheet
+    ActivePage = LazarusTabSheet
     Anchors = [akTop, akLeft, akRight, akBottom]
     BorderSpacing.Right = 6
-    TabIndex = 2
+    TabIndex = 0
     TabOrder = 3
     OnChange = PropertiesPageControlChange
     Options = [nboHidePageListPopup]
@@ -96,11 +96,11 @@
       ChildSizing.TopBottomSpacing = 6
       ChildSizing.HorizontalSpacing = 6
       ChildSizing.VerticalSpacing = 6
-      ClientHeight = 255
-      ClientWidth = 442
+      ClientHeight = 258
+      ClientWidth = 436
       object LazDirLabel: TLabel
         Left = 6
-        Height = 14
+        Height = 15
         Top = 6
         Width = 424
         Align = alTop
@@ -115,11 +115,11 @@
         AnchorSideRight.Control = LazarusTabSheet
         AnchorSideRight.Side = asrBottom
         Left = 6
-        Height = 21
-        Top = 26
+        Height = 23
+        Top = 27
         Width = 424
         Anchors = [akTop, akLeft, akRight]
-        ItemHeight = 0
+        ItemHeight = 15
         OnChange = LazDirComboBoxChange
         TabOrder = 0
         Text = 'LazDirComboBox'
@@ -128,8 +128,8 @@
         AnchorSideTop.Control = LazDirBrowseButton
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 174
-        Top = 82
+        Height = 165
+        Top = 87
         Width = 424
         Align = alBottom
         Anchors = [akTop, akLeft, akRight, akBottom]
@@ -148,9 +148,9 @@
         AnchorSideTop.Side = asrBottom
         AnchorSideRight.Side = asrBottom
         Left = 6
-        Height = 23
-        Top = 53
-        Width = 122
+        Height = 25
+        Top = 56
+        Width = 132
         AutoSize = True
         Caption = 'LazDirBrowseButton'
         OnClick = LazDirBrowseButtonClick
@@ -163,13 +163,13 @@
       ChildSizing.TopBottomSpacing = 6
       ChildSizing.HorizontalSpacing = 6
       ChildSizing.VerticalSpacing = 6
-      ClientHeight = 250
-      ClientWidth = 438
+      ClientHeight = 258
+      ClientWidth = 436
       object CompilerLabel: TLabel
         Left = 6
-        Height = 17
+        Height = 15
         Top = 6
-        Width = 426
+        Width = 424
         Align = alTop
         Caption = 'CompilerLabel'
         ParentColor = False
@@ -182,11 +182,11 @@
         AnchorSideRight.Control = CompilerTabSheet
         AnchorSideRight.Side = asrBottom
         Left = 6
-        Height = 21
-        Top = 29
-        Width = 426
+        Height = 23
+        Top = 27
+        Width = 424
         Anchors = [akTop, akLeft, akRight]
-        ItemHeight = 0
+        ItemHeight = 15
         OnChange = CompilerComboBoxChange
         TabOrder = 0
         Text = 'CompilerComboBox'
@@ -196,9 +196,9 @@
         AnchorSideTop.Control = CompilerComboBox
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 20
+        Height = 25
         Top = 56
-        Width = 168
+        Width = 149
         AutoSize = True
         Caption = 'CompilerBrowseButton'
         OnClick = CompilerBrowseButtonClick
@@ -213,9 +213,9 @@
         AnchorSideBottom.Control = CompilerTabSheet
         AnchorSideBottom.Side = asrBottom
         Left = 6
-        Height = 162
-        Top = 82
-        Width = 426
+        Height = 165
+        Top = 87
+        Width = 424
         Anchors = [akTop, akLeft, akRight, akBottom]
         Lines.Strings = (
           'CompilerMemo'
@@ -232,13 +232,13 @@
       ChildSizing.TopBottomSpacing = 6
       ChildSizing.HorizontalSpacing = 6
       ChildSizing.VerticalSpacing = 6
-      ClientHeight = 250
-      ClientWidth = 438
+      ClientHeight = 258
+      ClientWidth = 436
       object FPCSrcDirLabel: TLabel
         Left = 6
-        Height = 17
+        Height = 15
         Top = 6
-        Width = 426
+        Width = 424
         Align = alTop
         Caption = 'FPCSrcDirLabel'
         ParentColor = False
@@ -246,11 +246,11 @@
       end
       object FPCSrcDirComboBox: TComboBox
         Left = 6
-        Height = 21
-        Top = 29
-        Width = 426
+        Height = 23
+        Top = 27
+        Width = 424
         Align = alTop
-        ItemHeight = 0
+        ItemHeight = 15
         OnChange = FPCSrcDirComboBoxChange
         TabOrder = 0
         Text = 'FPCSrcDirComboBox'
@@ -260,9 +260,9 @@
         AnchorSideTop.Control = FPCSrcDirComboBox
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 20
+        Height = 25
         Top = 56
-        Width = 171
+        Width = 152
         AutoSize = True
         Caption = 'FPCSrcDirBrowseButton'
         OnClick = FPCSrcDirBrowseButtonClick
@@ -272,9 +272,9 @@
         AnchorSideTop.Control = FPCSrcDirBrowseButton
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 162
-        Top = 82
-        Width = 426
+        Height = 165
+        Top = 87
+        Width = 424
         Align = alBottom
         Anchors = [akTop, akLeft, akRight, akBottom]
         Lines.Strings = (
@@ -286,6 +286,118 @@
         TabOrder = 2
       end
     end
+    object MakeExeTabSheet: TTabSheet
+      Caption = 'MakeExeTabSheet'
+      ClientHeight = 258
+      ClientWidth = 436
+      object MakeExeComboBox: TComboBox
+        Left = 0
+        Height = 23
+        Top = 15
+        Width = 436
+        Align = alTop
+        ItemHeight = 15
+        OnChange = MakeExeComboBoxChange
+        TabOrder = 0
+        Text = 'MakeExeComboBox'
+      end
+      object MakeExeLabel: TLabel
+        Left = 0
+        Height = 15
+        Top = 0
+        Width = 436
+        Align = alTop
+        Caption = 'MakeExeLabel'
+        ParentColor = False
+        WordWrap = True
+      end
+      object MakeExeBrowseButton: TButton
+        AnchorSideLeft.Control = FPCSourcesTabSheet
+        AnchorSideTop.Control = MakeExeComboBox
+        AnchorSideTop.Side = asrBottom
+        Left = 6
+        Height = 25
+        Top = 38
+        Width = 146
+        AutoSize = True
+        Caption = 'MakeExeBrowseButton'
+        OnClick = MakeExeBrowseButtonClick
+        TabOrder = 1
+      end
+      object MakeExeMemo: TMemo
+        AnchorSideTop.Control = MakeExeBrowseButton
+        AnchorSideTop.Side = asrBottom
+        Left = 0
+        Height = 195
+        Top = 63
+        Width = 436
+        Align = alBottom
+        Anchors = [akTop, akLeft, akRight, akBottom]
+        Lines.Strings = (
+          'FPCSrcDirMemo'
+          ''
+          ''
+        )
+        ReadOnly = True
+        TabOrder = 2
+      end
+    end
+    object DebuggerTabSheet: TTabSheet
+      Caption = 'DebuggerTabSheet'
+      ClientHeight = 258
+      ClientWidth = 436
+      object DebuggerComboBox: TComboBox
+        Left = 0
+        Height = 23
+        Top = 15
+        Width = 436
+        Align = alTop
+        ItemHeight = 15
+        OnChange = DebuggerComboBoxChange
+        TabOrder = 0
+        Text = 'DebuggerComboBox'
+      end
+      object DebuggerLabel: TLabel
+        Left = 0
+        Height = 15
+        Top = 0
+        Width = 436
+        Align = alTop
+        Caption = 'DebuggerLabel'
+        ParentColor = False
+        WordWrap = True
+      end
+      object DebuggerBrowseButton: TButton
+        AnchorSideLeft.Control = FPCSourcesTabSheet
+        AnchorSideTop.Control = DebuggerComboBox
+        AnchorSideTop.Side = asrBottom
+        Left = 6
+        Height = 25
+        Top = 38
+        Width = 152
+        AutoSize = True
+        Caption = 'DebuggerBrowseButton'
+        OnClick = DebuggerBrowseButtonClick
+        TabOrder = 1
+      end
+      object DebuggerMemo: TMemo
+        AnchorSideTop.Control = DebuggerBrowseButton
+        AnchorSideTop.Side = asrBottom
+        Left = 0
+        Height = 195
+        Top = 63
+        Width = 436
+        Align = alBottom
+        Anchors = [akTop, akLeft, akRight, akBottom]
+        Lines.Strings = (
+          'FPCSrcDirMemo'
+          ''
+          ''
+        )
+        ReadOnly = True
+        TabOrder = 2
+      end
+    end
   end
   object WelcomePaintBox: TPaintBox
     Left = 0
Index: ide/initialsetupdlgs.pas
===================================================================
--- ide/initialsetupdlgs.pas	(revision 38091)
+++ ide/initialsetupdlgs.pas	(working copy)
@@ -67,7 +67,9 @@
   TSDFilenameType = (
     sddtLazarusSrcDir,
     sddtCompilerFilename,
-    sddtFPCSrcDir
+    sddtFPCSrcDir,
+    sddtMakeExeFilename,
+    sddtDebuggerFilename
     );
 
   { TInitialSetupDialog }
@@ -79,9 +81,17 @@
     CompilerLabel: TLabel;
     CompilerMemo: TMemo;
     FPCSrcDirBrowseButton: TButton;
+    MakeExeBrowseButton: TButton;
+    DebuggerBrowseButton: TButton;
     FPCSrcDirComboBox: TComboBox;
+    MakeExeComboBox: TComboBox;
+    DebuggerComboBox: TComboBox;
     FPCSrcDirLabel: TLabel;
+    MakeExeLabel: TLabel;
+    DebuggerLabel: TLabel;
     FPCSrcDirMemo: TMemo;
+    MakeExeMemo: TMemo;
+    DebuggerMemo: TMemo;
     ImageList1: TImageList;
     LazDirBrowseButton: TButton;
     LazDirLabel: TLabel;
@@ -94,15 +104,21 @@
     LazarusTabSheet: TTabSheet;
     CompilerTabSheet: TTabSheet;
     FPCSourcesTabSheet: TTabSheet;
+    MakeExeTabSheet: TTabSheet;
+    DebuggerTabSheet: TTabSheet;
     WelcomePaintBox: TPaintBox;
     procedure CompilerBrowseButtonClick(Sender: TObject);
     procedure CompilerComboBoxChange(Sender: TObject);
+    procedure DebuggerBrowseButtonClick(Sender: TObject);
+    procedure DebuggerComboBoxChange(Sender: TObject);
     procedure FormCreate(Sender: TObject);
     procedure FormDestroy(Sender: TObject);
     procedure FPCSrcDirBrowseButtonClick(Sender: TObject);
     procedure FPCSrcDirComboBoxChange(Sender: TObject);
     procedure LazDirBrowseButtonClick(Sender: TObject);
     procedure LazDirComboBoxChange(Sender: TObject);
+    procedure MakeExeBrowseButtonClick(Sender: TObject);
+    procedure MakeExeComboBoxChange(Sender: TObject);
     procedure PropertiesPageControlChange(Sender: TObject);
     procedure PropertiesTreeViewSelectionChanged(Sender: TObject);
     procedure StartIDEBitBtnClick(Sender: TObject);
@@ -111,9 +127,13 @@
   private
     FLazarusDirChanged: boolean;
     fCompilerFilenameChanged: boolean;
+    fMakeExeFilenameChanged: boolean;
+    fDebuggerFilenameChanged: boolean;
     FLastParsedLazDir: string;
     fLastParsedCompiler: string;
     fLastParsedFPCSrcDir: string;
+    fLastParsedMakeExe: string;
+    fLastParsedDebugger: string;
     FIdleConnected: boolean;
     ImgIDError: LongInt;
     ImgIDWarning: LongInt;
@@ -125,12 +145,16 @@
     procedure UpdateLazarusDirCandidates;
     procedure UpdateCompilerFilenameCandidates;
     procedure UpdateFPCSrcDirCandidates;
+    procedure UpdateMakeExeCandidates;
+    procedure UpdateDebuggerCandidates;
     procedure FillComboboxWithFileInfoList(ABox: TComboBox; List: TObjectList;
        ItemIndex: integer = 0);
     procedure SetIdleConnected(const AValue: boolean);
     procedure UpdateLazDirNote;
     procedure UpdateCompilerNote;
     procedure UpdateFPCSrcDirNote;
+    procedure UpdateMakeExeNote;
+    procedure UpdateDebuggerNote;
     function FirstErrorNode: TTreeNode;
     function GetFPCVer: string;
     function GetFirstCandidate(Candidates: TObjectList;
@@ -140,7 +164,9 @@
     TVNodeLazarus: TTreeNode;
     TVNodeCompiler: TTreeNode;
     TVNodeFPCSources: TTreeNode;
-    procedure Init;
+    TVNodeMakeExe: TTreeNode;
+    TVNodeDebugger: TTreeNode;
+    procedure Init; //Check for config errors, find and show alternatives
     property IdleConnected: boolean read FIdleConnected write SetIdleConnected;
   end;
 
@@ -164,10 +190,15 @@
 procedure SetupFPCSrcDir(FPCVer: string);
 
 function CheckMakeExeQuality(AFilename: string;
-  out Note: string): TSDFilenameQuality;
-function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList;
-procedure SetupMakeExe;
+  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid make executable
+function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList; //Search make candidates and add them to the list, including quality level
+procedure SetupMakeExe; //Checks if the make specified in user's options (if any) is ok. If not, search for and set a valid one if possible
 
+function CheckDebuggerQuality(AFilename: string;
+  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid debugger (only gdb supported for now)
+function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList; //Search debugger candidates and add them to list, including quality level
+procedure SetupDebugger; //Checks if the debugger specified in user's option (if any) is ok. If not, search for and set a valid one if possible
+
 function GetValueFromPrimaryConfig(OptionFilename, Path: string): string;
 function GetValueFromSecondaryConfig(OptionFilename, Path: string): string;
 function GetValueFromIDEConfig(OptionFilename, Path: string): string;
@@ -565,7 +596,7 @@
 
     // check $(LazarusDir)\fpc\bin\i386-win32\fpc.exe
     if CheckFile(SetDirSeparators('$(LazarusDir)/fpc/bin/$(TargetCPU)-$(TargetOS)/')+ShortCompFile,Result)
-    then exit;
+      then exit;
 
     // check common directories
     Files:=TStringList.Create;
@@ -577,8 +608,8 @@
       Files.Free;
     end;
 
+    // Windows-only locations:
     if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
-      // Windows has some special places
       SysDrive:=GetEnvironmentVariableUTF8('SYSTEMDRIVE');
       if SysDrive='' then SysDrive:='C:';
       SysDrive:=AppendPathDelim(SysDrive);
@@ -842,6 +873,165 @@
   end;
 end;
 
+function CheckDebuggerQuality(AFilename: string; out Note: string
+  ): TSDFilenameQuality;
+begin
+  Result:=sddqInvalid;
+  AFilename:=TrimFilename(AFilename);
+  if not FileExistsCached(AFilename) then
+  begin
+    Note:=lisFileNotFound4;
+    exit;
+  end;
+  if DirPathExistsCached(AFilename) then
+  begin
+    Note:=lisFileIsDirectory;
+    exit;
+  end;
+  if not FileIsExecutableCached(AFilename) then
+  begin
+    Note:=lisFileIsNotAnExecutable;
+    exit;
+  end;
+
+  { We could call gdb and parse the output looking for something like
+  GNU gdb, but that may be going too far. }
+  Note:=lisOk;
+  Result:=sddqCompatible;
+end;
+
+function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList;
+
+  function CheckFile(AFilename: string; var List: TObjectList): boolean;
+  var
+    Item: TSDFileInfo;
+    RealFilename: String;
+  begin
+    Result:=false;
+    if AFilename='' then exit;
+    DoDirSeparators(AFilename);
+    // check if already checked
+    if CaptionInSDFileList(AFilename,List) then exit;
+    EnvironmentOptions.DebuggerFilename:=AFilename;
+    RealFilename:=EnvironmentOptions.GetParsedDebuggerFilename;
+    debugln(['SearchDebuggerCandidates Value=',AFilename,' File=',RealFilename]);
+    if RealFilename='' then exit;
+    // check if exists
+    if not FileExistsCached(RealFilename) then exit;
+    // add to list and check quality
+    Item:=TSDFileInfo.Create;
+    Item.Filename:=RealFilename;
+    Item.Quality:=CheckDebuggerQuality(RealFilename,Item.Note);
+    Item.Caption:=AFilename;
+    if List=nil then
+      List:=TObjectList.create(true);
+    List.Add(Item);
+    Result:=(Item.Quality=sddqCompatible) and StopIfFits;
+  end;
+const
+  DebuggerFileName='gdb'; //For Windows, .exe will be appended
+var
+  OldDebuggerFilename: String;
+  AFilename: String;
+  Files: TStringList;
+  i: Integer;
+begin
+  Result:=nil;
+
+  OldDebuggerFilename:=EnvironmentOptions.DebuggerFilename;
+  try
+    // check current setting
+    if CheckFile(EnvironmentOptions.DebuggerFilename,Result) then exit;
+
+    // check the primary options
+    AFilename:=GetValueFromPrimaryConfig(EnvOptsConfFileName,
+                                    'EnvironmentOptions/DebuggerFilename/Value');
+    if CheckFile(AFilename,Result) then exit;
+
+    // check the secondary options
+    AFilename:=GetValueFromSecondaryConfig(EnvOptsConfFileName,
+                                    'EnvironmentOptions/DebuggerFilename/Value');
+    if CheckFile(AFilename,Result) then exit;
+
+    // The next 2 locations are locations used by older and newer versions of the Windows installers
+    // If other platform installers follow the same strategy, this can be useful.
+    // Chances of this are low (gdb is generally installed in the path on Unixy systems), but it can't hurt...
+    // and it can be useful for cross compiling/custom setups.
+
+    // Check new installation location: $(LazarusDir)\mingw\$(TargetCPU)-$(TargetOS)\bin\gdb.exe
+    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/$(TargetCPU)-$(TargetOS)/bin/'+DebuggerFileName+GetExecutableExt),Result)
+      then exit;
+
+    // Older Lazarus installers did not use macros for their debuggers: there was only one debugger
+    // Check old installation location: $(LazarusDir)\mingw\bin\gdb.exe
+    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/bin/'+DebuggerFileName+GetExecutableExt),Result)
+      then exit;
+
+    // Windows-only locations:
+    if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
+      // check for debugger in fpc.exe directory - could be a lucky shot
+      if CheckFile(SetDirSeparators('$Path($(CompPath))/'+DebuggerFileName+GetExecutableExt),Result)
+        then exit;
+    end;
+
+    // check history
+    Files:=EnvironmentOptions.DebuggerFileHistory;
+    if Files<>nil then
+      for i:=0 to Files.Count-1 do
+        if CheckFile(Files[i],Result) then exit;
+
+    // check PATH
+    AFilename:=DebuggerFileName;
+    AFilename+=GetExecutableExt;
+    if CheckFile(FindDefaultExecutablePath(AFilename),Result) then exit;
+
+    // There are no common directories apart from the PATH
+    // where gdb would be installed. Otherwise we could do something similar as
+    // in SearchMakeExeCandidates.
+  finally
+    EnvironmentOptions.DebuggerFilename:=OldDebuggerFilename;
+  end;
+end;
+
+procedure SetupDebugger;
+var
+  Note: string;
+  Filename: String;
+  Quality: TSDFilenameQuality;
+  BestDir: TSDFileInfo;
+  List: TObjectList;
+begin
+  Filename:=EnvironmentOptions.GetParsedDebuggerFilename;
+  Quality:=CheckDebuggerQuality(Filename,Note);
+  if Quality<>sddqInvalid then exit;
+  // bad debugger
+  dbgout('SetupDebugger:');
+  if EnvironmentOptions.DebuggerFilename<>'' then
+  begin
+    dbgout(' The "gdb" executable "',EnvironmentOptions.DebuggerFilename,'"');
+    if EnvironmentOptions.DebuggerFilename<>Filename then
+      dbgout(' => "',Filename,'"');
+    dbgout(' is invalid (Error: ',Note,')');
+    debugln(' Searching a proper one ...');
+  end else begin
+    debugln(' Searching "gdb" ...');
+  end;
+  List:=SearchDebuggerCandidates(true);
+  try
+    BestDir:=nil;
+    if List<>nil then
+      BestDir:=TSDFileInfo(List[List.Count-1]);
+    if (BestDir=nil) or (BestDir.Quality=sddqInvalid) then begin
+      debugln(['SetupDebugger: no proper "gdb" found.']);
+      exit;
+    end;
+    EnvironmentOptions.DebuggerFilename:=BestDir.Filename;
+    debugln(['SetupDebugger: using ',EnvironmentOptions.DebuggerFilename]);
+  finally
+    List.Free;
+  end;
+end;
+
 function CheckMakeExeQuality(AFilename: string; out Note: string
   ): TSDFilenameQuality;
 begin
@@ -863,11 +1053,13 @@
     exit;
   end;
 
+  // Windows-only locations:
   if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
-    // under Windows the make.exe is in the same directory as fpc.exe
+    // under Windows, make.exe is in the same directory as fpc.exe
     if not FileExistsCached(ExtractFilePath(AFilename)+'fpc.exe') then begin
-      Note:='There is no fpc.exe in the directory of the '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the fpc compiler.';
+      Note:='There is no fpc.exe in the directory of '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the FPC compiler.';
       Result:=sddqIncomplete;
+      exit;
     end;
   end;
 
@@ -926,6 +1118,7 @@
                                     'EnvironmentOptions/MakeFilename/Value');
     if CheckFile(AFilename,Result) then exit;
 
+    // Windows-only locations:
     if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
       // check make in fpc.exe directory
       if CheckFile(SetDirSeparators('$Path($(CompPath))/make.exe'),Result)
@@ -1098,6 +1291,8 @@
   LazarusTabSheet.Caption:='Lazarus';
   CompilerTabSheet.Caption:=lisCompiler;
   FPCSourcesTabSheet.Caption:=lisFPCSources;
+  MakeExeTabSheet.Caption:='make';
+  DebuggerTabSheet.Caption:=lisDebugger;
 
   FHeadGraphic:=TPortableNetworkGraphic.Create;
   FHeadGraphic.LoadFromLazarusResource('ide_icon48x48');
@@ -1105,6 +1300,8 @@
   TVNodeLazarus:=PropertiesTreeView.Items.Add(nil,LazarusTabSheet.Caption);
   TVNodeCompiler:=PropertiesTreeView.Items.Add(nil,CompilerTabSheet.Caption);
   TVNodeFPCSources:=PropertiesTreeView.Items.Add(nil,FPCSourcesTabSheet.Caption);
+  TVNodeMakeExe:=PropertiesTreeView.Items.Add(nil,MakeExeTabSheet.Caption);
+  TVNodeDebugger:=PropertiesTreeView.Items.Add(nil,DebuggerTabSheet.Caption);
   ImgIDError := ImageList1.AddLazarusResource('state_error');
   ImgIDWarning := ImageList1.AddLazarusResource('state_warning');
 
@@ -1122,6 +1319,15 @@
   FPCSrcDirLabel.Caption:=Format(
     lisTheSourcesOfTheFreePascalPackagesAreRequiredForBro, [SetDirSeparators('rtl'
     +'/linux/system.pp')]);
+
+  MakeExeBrowseButton.Caption:=lisPathEditBrowse;
+  MakeExeLabel.Caption:=Format(
+    lisTheMakeExecutableTypicallyHasTheName, ['make'+GetExecutableExt('')]);
+
+  DebuggerBrowseButton.Caption:=lisPathEditBrowse;
+  DebuggerLabel.Caption:=Format(
+    lisTheDebuggerExecutableTypicallyHasTheName, ['gdb'+GetExecutableExt('')]);
+
 end;
 
 procedure TInitialSetupDialog.CompilerComboBoxChange(Sender: TObject);
@@ -1129,6 +1335,35 @@
   UpdateCompilerNote;
 end;
 
+procedure TInitialSetupDialog.DebuggerBrowseButtonClick(Sender: TObject);
+var
+  Filename: String;
+  Dlg: TOpenDialog;
+  Filter: String;
+begin
+  Dlg:=TOpenDialog.Create(nil);
+  try
+    Filename:='gdb'+GetExecutableExt;
+    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
+    Dlg.Options:=Dlg.Options+[ofFileMustExist];
+    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
+    if ExtractFileExt(Filename)<>'' then
+      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
+    Dlg.Filter:=Filter;
+    if not Dlg.Execute then exit;
+    Filename:=Dlg.FileName;
+  finally
+    Dlg.Free;
+  end;
+  DebuggerComboBox.Text:=Filename;
+  UpdateDebuggerNote;
+end;
+
+procedure TInitialSetupDialog.DebuggerComboBoxChange(Sender: TObject);
+begin
+  UpdateDebuggerNote;
+end;
+
 procedure TInitialSetupDialog.CompilerBrowseButtonClick(Sender: TObject);
 var
   Filename: String;
@@ -1193,6 +1428,35 @@
   UpdateLazDirNote;
 end;
 
+procedure TInitialSetupDialog.MakeExeBrowseButtonClick(Sender: TObject);
+var
+  Filename: String;
+  Dlg: TOpenDialog;
+  Filter: String;
+begin
+  Dlg:=TOpenDialog.Create(nil);
+  try
+    Filename:='make'+GetExecutableExt;
+    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
+    Dlg.Options:=Dlg.Options+[ofFileMustExist];
+    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
+    if ExtractFileExt(Filename)<>'' then
+      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
+    Dlg.Filter:=Filter;
+    if not Dlg.Execute then exit;
+    Filename:=Dlg.FileName;
+  finally
+    Dlg.Free;
+  end;
+  MakeExeComboBox.Text:=Filename;
+  UpdateMakeExeNote;
+end;
+
+procedure TInitialSetupDialog.MakeExeComboBoxChange(Sender: TObject);
+begin
+  UpdateMakeExeNote;
+end;
+
 procedure TInitialSetupDialog.PropertiesPageControlChange(Sender: TObject);
 var
   s: String;
@@ -1225,7 +1489,11 @@
   else if Node=TVNodeCompiler then
     s:=lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW
   else if Node=TVNodeFPCSources then
-    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio;
+    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio
+  else if Node=TVNodeMakeExe then
+    s:=lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp
+  else if Node=TVNodeDebugger then
+    s:=lisWithoutAProperDebuggerDebuggingWillBeDisappointing;
   if s<>'' then begin
     MsgResult:=MessageDlg(lisCCOWarningCaption, s, mtWarning, [mbIgnore,
       mbCancel], 0);
@@ -1241,9 +1509,13 @@
   s:=FPCSrcDirComboBox.Text;
   if s<>'' then
     EnvironmentOptions.FPCSourceDirectory:=s;
+  s:=MakeExeComboBox.Text;
+  if s<>'' then
+    EnvironmentOptions.MakeFilename:=s;
+  s:=DebuggerComboBox.Text;
+  if s<>'' then
+    EnvironmentOptions.DebuggerFilename:=s;
 
-  SetupMakeExe;
-
   ModalResult:=mrOk;
 end;
 
@@ -1267,6 +1539,12 @@
   end else if fCompilerFilenameChanged then begin
     UpdateFPCSrcDirCandidates;
     UpdateFPCSrcDirNote;
+  end else if fMakeExeFilenameChanged then begin
+    UpdateMakeExeCandidates;
+    UpdateMakeExeNote;
+  end else if fDebuggerFilenameChanged then begin
+    UpdateDebuggerCandidates;
+    UpdateDebuggerNote;
   end else
     IdleConnected:=false;
 end;
@@ -1341,6 +1619,28 @@
   FillComboboxWithFileInfoList(FPCSrcDirComboBox,Dirs);
 end;
 
+procedure TInitialSetupDialog.UpdateMakeExeCandidates;
+var
+  Files: TObjectList;
+begin
+  FLazarusDirChanged:=false;
+  Files:=SearchMakeExeCandidates(false);
+  FreeAndNil(FCandidates[sddtMakeExeFileName]);
+  FCandidates[sddtMakeExeFileName]:=Files;
+  FillComboboxWithFileInfoList(MakeExeComboBox,Files);
+end;
+
+procedure TInitialSetupDialog.UpdateDebuggerCandidates;
+var
+  Files: TObjectList;
+begin
+  FLazarusDirChanged:=false;
+  Files:=SearchDebuggerCandidates(false);
+  FreeAndNil(FCandidates[sddtDebuggerFilename]);
+  FCandidates[sddtDebuggerFilename]:=Files;
+  FillComboboxWithFileInfoList(DebuggerComboBox,Files);
+end;
+
 procedure TInitialSetupDialog.FillComboboxWithFileInfoList(ABox: TComboBox;
   List: TObjectList; ItemIndex: integer);
 var
@@ -1479,6 +1779,76 @@
   TVNodeFPCSources.SelectedIndex:=ImageIndex;
 end;
 
+procedure TInitialSetupDialog.UpdateMakeExeNote;
+var
+  CurCaption: String;
+  Note: string;
+  Quality: TSDFilenameQuality;
+  s: String;
+  ImageIndex: Integer;
+begin
+  if csDestroying in ComponentState then exit;
+  CurCaption:=MakeExeComboBox.Text;
+  EnvironmentOptions.MakeFilename:=CurCaption;
+  if fLastParsedMakeExe=EnvironmentOptions.GetParsedMakeFilename then exit;
+  fLastParsedMakeExe:=EnvironmentOptions.GetParsedMakeFilename;
+  //debugln(['TInitialSetupDialog.UpdateMakeExeNote ',fLastParsedMakeExe]);
+  Quality:=CheckMakeExeQuality(fLastParsedMakeExe,Note);
+
+  case Quality of
+  sddqInvalid: s:=lisError;
+  sddqCompatible: s:='';
+  else s:=lisWarning;
+  end;
+  if EnvironmentOptions.MakeFilename<>EnvironmentOptions.GetParsedMakeFilename
+  then
+    s:=lisFile2+EnvironmentOptions.GetParsedMakeFilename+LineEnding+
+      LineEnding+s;
+  MakeExeMemo.Text:=s+Note;
+
+  ImageIndex:=QualityToImgIndex(Quality);
+  TVNodeMakeExe.ImageIndex:=ImageIndex;
+  TVNodeMakeExe.SelectedIndex:=ImageIndex;
+
+  fMakeExeFilenameChanged:=true;
+  IdleConnected:=true;
+end;
+
+procedure TInitialSetupDialog.UpdateDebuggerNote;
+var
+  CurCaption: String;
+  Note: string;
+  Quality: TSDFilenameQuality;
+  s: String;
+  ImageIndex: Integer;
+begin
+  if csDestroying in ComponentState then exit;
+  CurCaption:=DebuggerComboBox.Text;
+  EnvironmentOptions.DebuggerFilename:=CurCaption;
+  if fLastParsedDebugger=EnvironmentOptions.GetParsedDebuggerFilename then exit;
+  fLastParsedDebugger:=EnvironmentOptions.GetParsedDebuggerFilename;
+  //debugln(['TInitialSetupDialog.UpdateDebuggerNote ',fLastParsedDebugger]);
+  Quality:=CheckDebuggerQuality(fLastParsedDebugger,Note);
+
+  case Quality of
+  sddqInvalid: s:=lisError;
+  sddqCompatible: s:='';
+  else s:=lisWarning;
+  end;
+  if EnvironmentOptions.DebuggerFilename<>EnvironmentOptions.GetParsedDebuggerFilename
+  then
+    s:=lisFile2+EnvironmentOptions.GetParsedDebuggerFilename+LineEnding+
+      LineEnding+s;
+  DebuggerMemo.Text:=s+Note;
+
+  ImageIndex:=QualityToImgIndex(Quality);
+  TVNodeDebugger.ImageIndex:=ImageIndex;
+  TVNodeDebugger.SelectedIndex:=ImageIndex;
+
+  fDebuggerFilenameChanged:=true;
+  IdleConnected:=true;
+end;
+
 function TInitialSetupDialog.FirstErrorNode: TTreeNode;
 var
   i: Integer;
@@ -1518,6 +1888,8 @@
     Result:=-1
   else if Quality=sddqWrongMinorVersion then
     Result:=ImgIDWarning
+  else if Quality=sddqIncomplete then
+    Result:=ImgIDWarning
   else
     Result:=ImgIDError;
 end;
@@ -1568,6 +1940,32 @@
   fLastParsedFPCSrcDir:='. .';
   UpdateFPCSrcDirNote;
 
+  // Make executable
+  UpdateMakeExeCandidates;
+  if (not FileExistsCached(EnvironmentOptions.Filename)) then
+  begin
+    // first start => choose first best candidate
+    Candidate:=GetFirstCandidate(FCandidates[sddtMakeExeFilename]);
+    if Candidate<>nil then
+      EnvironmentOptions.MakeFilename:=Candidate.Caption;
+  end;
+  MakeExeComboBox.Text:=EnvironmentOptions.MakeFilename;
+  fLastParsedMakeExe:='. .';
+  UpdateMakeExeNote;
+
+  // Debugger
+  UpdateDebuggerCandidates;
+  if (not FileExistsCached(EnvironmentOptions.Filename)) then
+  begin
+    // first start => choose first best candidate
+    Candidate:=GetFirstCandidate(FCandidates[sddtDebuggerFilename]);
+    if Candidate<>nil then
+      EnvironmentOptions.DebuggerFilename:=Candidate.Caption;
+  end;
+  DebuggerComboBox.Text:=EnvironmentOptions.DebuggerFilename;
+  fLastParsedDebugger:='. .';
+  UpdateDebuggerNote;
+
   // select first error
   Node:=FirstErrorNode;
   if Node=nil then
Index: ide/lazarusidestrconsts.pas
===================================================================
--- ide/lazarusidestrconsts.pas	(revision 38091)
+++ ide/lazarusidestrconsts.pas	(working copy)
@@ -2008,6 +2008,7 @@
   dlgCOLibraries = 'Libraries (-Fl):';
   dlgCODebugPath = 'Debugger path addition (none):';
   lisCompiler = 'Compiler';
+  lisDebugger = 'Debugger';
   lisToFPCPath = 'Path:';
   lisCOSkipCallingCompiler = 'Skip calling compiler';
   lisCOAmbiguousAdditionalCompilerConfigFile = 'Ambiguous additional compiler '
@@ -5437,6 +5438,10 @@
     +'Lazarus directory you will get a lot of warnings.';
   lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW = 'Without a proper '
     +'compiler the code browsing and compiling will be disappointing.';
+  lisWithoutAProperDebuggerDebuggingWillBeDisappointing = 'Without a proper '
+    +'debugger, debugging will be disappointing.';
+  lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp = 'Without a proper '
+    +'make executable the code browsing and compiling will be disappointing.';
   lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio = 'Without the proper '
     +'FPC sources code browsing and completion will be very limited.';
   lisTheLazarusDirectoryContainsTheSourcesOfTheIDEAndTh = 'The Lazarus '
@@ -5446,6 +5451,11 @@
   lisTheFreePascalCompilerExecutableTypicallyHasTheName = 'The Free Pascal '
     +'compiler executable typically has the name "%s". You can also use the '
     +'target specific compiler like "%s". Please give the full file path.';
+  lisTheMakeExecutableTypicallyHasTheName = 'The make executable typically '
+    +'has the name "%s". Please give the full file path.';
+  lisTheDebuggerExecutableTypicallyHasTheName = 'The debugger executable '
+    +'typically has the name "%s". Pleae give the full file path. '
+    +'A useful setting on Windows systems is: $(LazarusDir)\mingw\bin\$(TargetCPU)-$(TargetOS)\gdb.exe';
   lisFoundVersionExpected = 'Found version %s, expected %s';
   lisInvalidVersionIn = 'invalid version in %s';
   lisWrongVersionIn = 'wrong version in %s: %s';

Reinier Olislagers

2012-07-31 12:51

developer   ~0061316

initial_checkdebugger3.diff: additional small refinements:
- some small grammar corrections
- if no errors but only warnings present, show first warning tab

2012-07-31 12:52

 

initial_checkdebugger3.diff (36,180 bytes)
Index: ide/initialsetupdlgs.lfm
===================================================================
--- ide/initialsetupdlgs.lfm	(revision 38091)
+++ ide/initialsetupdlgs.lfm	(working copy)
@@ -1,8 +1,8 @@
 object InitialSetupDialog: TInitialSetupDialog
   AnchorSideBottom.Side = asrBottom
-  Left = 253
+  Left = 319
   Height = 385
-  Top = 253
+  Top = 238
   Width = 620
   Caption = 'InitialSetupDialog'
   ClientHeight = 385
@@ -10,7 +10,7 @@
   OnCreate = FormCreate
   OnDestroy = FormDestroy
   Position = poScreenCenter
-  LCLVersion = '0.9.31'
+  LCLVersion = '1.1'
   object PropertiesTreeView: TTreeView
     AnchorSideLeft.Control = Owner
     AnchorSideTop.Control = WelcomePaintBox
@@ -18,7 +18,7 @@
     AnchorSideRight.Control = Splitter1
     AnchorSideBottom.Control = BtnPanel
     Left = 6
-    Height = 289
+    Height = 286
     Top = 54
     Width = 159
     Anchors = [akTop, akLeft, akRight, akBottom]
@@ -40,7 +40,7 @@
     AnchorSideBottom.Control = PropertiesTreeView
     AnchorSideBottom.Side = asrBottom
     Left = 165
-    Height = 289
+    Height = 286
     Top = 54
     Width = 5
     Align = alNone
@@ -48,21 +48,21 @@
   end
   object BtnPanel: TPanel
     Left = 10
-    Height = 22
-    Top = 353
+    Height = 25
+    Top = 350
     Width = 600
     Align = alBottom
     AutoSize = True
     BorderSpacing.Around = 10
     BevelOuter = bvNone
-    ClientHeight = 22
+    ClientHeight = 25
     ClientWidth = 600
     TabOrder = 2
     object StartIDEBitBtn: TBitBtn
-      Left = 489
-      Height = 22
+      Left = 500
+      Height = 25
       Top = 0
-      Width = 111
+      Width = 100
       Align = alRight
       AutoSize = True
       Caption = 'StartIDEBitBtn'
@@ -80,13 +80,13 @@
     AnchorSideBottom.Control = Splitter1
     AnchorSideBottom.Side = asrBottom
     Left = 170
-    Height = 289
+    Height = 286
     Top = 54
     Width = 444
-    ActivePage = FPCSourcesTabSheet
+    ActivePage = LazarusTabSheet
     Anchors = [akTop, akLeft, akRight, akBottom]
     BorderSpacing.Right = 6
-    TabIndex = 2
+    TabIndex = 0
     TabOrder = 3
     OnChange = PropertiesPageControlChange
     Options = [nboHidePageListPopup]
@@ -96,11 +96,11 @@
       ChildSizing.TopBottomSpacing = 6
       ChildSizing.HorizontalSpacing = 6
       ChildSizing.VerticalSpacing = 6
-      ClientHeight = 255
-      ClientWidth = 442
+      ClientHeight = 258
+      ClientWidth = 436
       object LazDirLabel: TLabel
         Left = 6
-        Height = 14
+        Height = 15
         Top = 6
         Width = 424
         Align = alTop
@@ -115,11 +115,11 @@
         AnchorSideRight.Control = LazarusTabSheet
         AnchorSideRight.Side = asrBottom
         Left = 6
-        Height = 21
-        Top = 26
+        Height = 23
+        Top = 27
         Width = 424
         Anchors = [akTop, akLeft, akRight]
-        ItemHeight = 0
+        ItemHeight = 15
         OnChange = LazDirComboBoxChange
         TabOrder = 0
         Text = 'LazDirComboBox'
@@ -128,8 +128,8 @@
         AnchorSideTop.Control = LazDirBrowseButton
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 174
-        Top = 82
+        Height = 165
+        Top = 87
         Width = 424
         Align = alBottom
         Anchors = [akTop, akLeft, akRight, akBottom]
@@ -148,9 +148,9 @@
         AnchorSideTop.Side = asrBottom
         AnchorSideRight.Side = asrBottom
         Left = 6
-        Height = 23
-        Top = 53
-        Width = 122
+        Height = 25
+        Top = 56
+        Width = 132
         AutoSize = True
         Caption = 'LazDirBrowseButton'
         OnClick = LazDirBrowseButtonClick
@@ -163,13 +163,13 @@
       ChildSizing.TopBottomSpacing = 6
       ChildSizing.HorizontalSpacing = 6
       ChildSizing.VerticalSpacing = 6
-      ClientHeight = 250
-      ClientWidth = 438
+      ClientHeight = 258
+      ClientWidth = 436
       object CompilerLabel: TLabel
         Left = 6
-        Height = 17
+        Height = 15
         Top = 6
-        Width = 426
+        Width = 424
         Align = alTop
         Caption = 'CompilerLabel'
         ParentColor = False
@@ -182,11 +182,11 @@
         AnchorSideRight.Control = CompilerTabSheet
         AnchorSideRight.Side = asrBottom
         Left = 6
-        Height = 21
-        Top = 29
-        Width = 426
+        Height = 23
+        Top = 27
+        Width = 424
         Anchors = [akTop, akLeft, akRight]
-        ItemHeight = 0
+        ItemHeight = 15
         OnChange = CompilerComboBoxChange
         TabOrder = 0
         Text = 'CompilerComboBox'
@@ -196,9 +196,9 @@
         AnchorSideTop.Control = CompilerComboBox
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 20
+        Height = 25
         Top = 56
-        Width = 168
+        Width = 149
         AutoSize = True
         Caption = 'CompilerBrowseButton'
         OnClick = CompilerBrowseButtonClick
@@ -213,9 +213,9 @@
         AnchorSideBottom.Control = CompilerTabSheet
         AnchorSideBottom.Side = asrBottom
         Left = 6
-        Height = 162
-        Top = 82
-        Width = 426
+        Height = 165
+        Top = 87
+        Width = 424
         Anchors = [akTop, akLeft, akRight, akBottom]
         Lines.Strings = (
           'CompilerMemo'
@@ -232,13 +232,13 @@
       ChildSizing.TopBottomSpacing = 6
       ChildSizing.HorizontalSpacing = 6
       ChildSizing.VerticalSpacing = 6
-      ClientHeight = 250
-      ClientWidth = 438
+      ClientHeight = 258
+      ClientWidth = 436
       object FPCSrcDirLabel: TLabel
         Left = 6
-        Height = 17
+        Height = 15
         Top = 6
-        Width = 426
+        Width = 424
         Align = alTop
         Caption = 'FPCSrcDirLabel'
         ParentColor = False
@@ -246,11 +246,11 @@
       end
       object FPCSrcDirComboBox: TComboBox
         Left = 6
-        Height = 21
-        Top = 29
-        Width = 426
+        Height = 23
+        Top = 27
+        Width = 424
         Align = alTop
-        ItemHeight = 0
+        ItemHeight = 15
         OnChange = FPCSrcDirComboBoxChange
         TabOrder = 0
         Text = 'FPCSrcDirComboBox'
@@ -260,9 +260,9 @@
         AnchorSideTop.Control = FPCSrcDirComboBox
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 20
+        Height = 25
         Top = 56
-        Width = 171
+        Width = 152
         AutoSize = True
         Caption = 'FPCSrcDirBrowseButton'
         OnClick = FPCSrcDirBrowseButtonClick
@@ -272,9 +272,9 @@
         AnchorSideTop.Control = FPCSrcDirBrowseButton
         AnchorSideTop.Side = asrBottom
         Left = 6
-        Height = 162
-        Top = 82
-        Width = 426
+        Height = 165
+        Top = 87
+        Width = 424
         Align = alBottom
         Anchors = [akTop, akLeft, akRight, akBottom]
         Lines.Strings = (
@@ -286,6 +286,118 @@
         TabOrder = 2
       end
     end
+    object MakeExeTabSheet: TTabSheet
+      Caption = 'MakeExeTabSheet'
+      ClientHeight = 258
+      ClientWidth = 436
+      object MakeExeComboBox: TComboBox
+        Left = 0
+        Height = 23
+        Top = 15
+        Width = 436
+        Align = alTop
+        ItemHeight = 15
+        OnChange = MakeExeComboBoxChange
+        TabOrder = 0
+        Text = 'MakeExeComboBox'
+      end
+      object MakeExeLabel: TLabel
+        Left = 0
+        Height = 15
+        Top = 0
+        Width = 436
+        Align = alTop
+        Caption = 'MakeExeLabel'
+        ParentColor = False
+        WordWrap = True
+      end
+      object MakeExeBrowseButton: TButton
+        AnchorSideLeft.Control = FPCSourcesTabSheet
+        AnchorSideTop.Control = MakeExeComboBox
+        AnchorSideTop.Side = asrBottom
+        Left = 6
+        Height = 25
+        Top = 38
+        Width = 146
+        AutoSize = True
+        Caption = 'MakeExeBrowseButton'
+        OnClick = MakeExeBrowseButtonClick
+        TabOrder = 1
+      end
+      object MakeExeMemo: TMemo
+        AnchorSideTop.Control = MakeExeBrowseButton
+        AnchorSideTop.Side = asrBottom
+        Left = 0
+        Height = 195
+        Top = 63
+        Width = 436
+        Align = alBottom
+        Anchors = [akTop, akLeft, akRight, akBottom]
+        Lines.Strings = (
+          'FPCSrcDirMemo'
+          ''
+          ''
+        )
+        ReadOnly = True
+        TabOrder = 2
+      end
+    end
+    object DebuggerTabSheet: TTabSheet
+      Caption = 'DebuggerTabSheet'
+      ClientHeight = 258
+      ClientWidth = 436
+      object DebuggerComboBox: TComboBox
+        Left = 0
+        Height = 23
+        Top = 15
+        Width = 436
+        Align = alTop
+        ItemHeight = 15
+        OnChange = DebuggerComboBoxChange
+        TabOrder = 0
+        Text = 'DebuggerComboBox'
+      end
+      object DebuggerLabel: TLabel
+        Left = 0
+        Height = 15
+        Top = 0
+        Width = 436
+        Align = alTop
+        Caption = 'DebuggerLabel'
+        ParentColor = False
+        WordWrap = True
+      end
+      object DebuggerBrowseButton: TButton
+        AnchorSideLeft.Control = FPCSourcesTabSheet
+        AnchorSideTop.Control = DebuggerComboBox
+        AnchorSideTop.Side = asrBottom
+        Left = 6
+        Height = 25
+        Top = 38
+        Width = 152
+        AutoSize = True
+        Caption = 'DebuggerBrowseButton'
+        OnClick = DebuggerBrowseButtonClick
+        TabOrder = 1
+      end
+      object DebuggerMemo: TMemo
+        AnchorSideTop.Control = DebuggerBrowseButton
+        AnchorSideTop.Side = asrBottom
+        Left = 0
+        Height = 195
+        Top = 63
+        Width = 436
+        Align = alBottom
+        Anchors = [akTop, akLeft, akRight, akBottom]
+        Lines.Strings = (
+          'FPCSrcDirMemo'
+          ''
+          ''
+        )
+        ReadOnly = True
+        TabOrder = 2
+      end
+    end
   end
   object WelcomePaintBox: TPaintBox
     Left = 0
Index: ide/initialsetupdlgs.pas
===================================================================
--- ide/initialsetupdlgs.pas	(revision 38091)
+++ ide/initialsetupdlgs.pas	(working copy)
@@ -67,7 +67,9 @@
   TSDFilenameType = (
     sddtLazarusSrcDir,
     sddtCompilerFilename,
-    sddtFPCSrcDir
+    sddtFPCSrcDir,
+    sddtMakeExeFilename,
+    sddtDebuggerFilename
     );
 
   { TInitialSetupDialog }
@@ -79,9 +81,17 @@
     CompilerLabel: TLabel;
     CompilerMemo: TMemo;
     FPCSrcDirBrowseButton: TButton;
+    MakeExeBrowseButton: TButton;
+    DebuggerBrowseButton: TButton;
     FPCSrcDirComboBox: TComboBox;
+    MakeExeComboBox: TComboBox;
+    DebuggerComboBox: TComboBox;
     FPCSrcDirLabel: TLabel;
+    MakeExeLabel: TLabel;
+    DebuggerLabel: TLabel;
     FPCSrcDirMemo: TMemo;
+    MakeExeMemo: TMemo;
+    DebuggerMemo: TMemo;
     ImageList1: TImageList;
     LazDirBrowseButton: TButton;
     LazDirLabel: TLabel;
@@ -94,15 +104,21 @@
     LazarusTabSheet: TTabSheet;
     CompilerTabSheet: TTabSheet;
     FPCSourcesTabSheet: TTabSheet;
+    MakeExeTabSheet: TTabSheet;
+    DebuggerTabSheet: TTabSheet;
     WelcomePaintBox: TPaintBox;
     procedure CompilerBrowseButtonClick(Sender: TObject);
     procedure CompilerComboBoxChange(Sender: TObject);
+    procedure DebuggerBrowseButtonClick(Sender: TObject);
+    procedure DebuggerComboBoxChange(Sender: TObject);
     procedure FormCreate(Sender: TObject);
     procedure FormDestroy(Sender: TObject);
     procedure FPCSrcDirBrowseButtonClick(Sender: TObject);
     procedure FPCSrcDirComboBoxChange(Sender: TObject);
     procedure LazDirBrowseButtonClick(Sender: TObject);
     procedure LazDirComboBoxChange(Sender: TObject);
+    procedure MakeExeBrowseButtonClick(Sender: TObject);
+    procedure MakeExeComboBoxChange(Sender: TObject);
     procedure PropertiesPageControlChange(Sender: TObject);
     procedure PropertiesTreeViewSelectionChanged(Sender: TObject);
     procedure StartIDEBitBtnClick(Sender: TObject);
@@ -111,9 +127,13 @@
   private
     FLazarusDirChanged: boolean;
     fCompilerFilenameChanged: boolean;
+    fMakeExeFilenameChanged: boolean;
+    fDebuggerFilenameChanged: boolean;
     FLastParsedLazDir: string;
     fLastParsedCompiler: string;
     fLastParsedFPCSrcDir: string;
+    fLastParsedMakeExe: string;
+    fLastParsedDebugger: string;
     FIdleConnected: boolean;
     ImgIDError: LongInt;
     ImgIDWarning: LongInt;
@@ -125,13 +145,17 @@
     procedure UpdateLazarusDirCandidates;
     procedure UpdateCompilerFilenameCandidates;
     procedure UpdateFPCSrcDirCandidates;
+    procedure UpdateMakeExeCandidates;
+    procedure UpdateDebuggerCandidates;
     procedure FillComboboxWithFileInfoList(ABox: TComboBox; List: TObjectList;
        ItemIndex: integer = 0);
     procedure SetIdleConnected(const AValue: boolean);
     procedure UpdateLazDirNote;
     procedure UpdateCompilerNote;
     procedure UpdateFPCSrcDirNote;
-    function FirstErrorNode: TTreeNode;
+    procedure UpdateMakeExeNote;
+    procedure UpdateDebuggerNote;
+    function FirstErrorNode(IncludeWarnings: boolean): TTreeNode; //Get first treeview node where an error is shown. If IncludeWarnings: return warning node if no error node found
     function GetFPCVer: string;
     function GetFirstCandidate(Candidates: TObjectList;
       MinQuality: TSDFilenameQuality = sddqCompatible): TSDFileInfo;
@@ -140,7 +164,9 @@
     TVNodeLazarus: TTreeNode;
     TVNodeCompiler: TTreeNode;
     TVNodeFPCSources: TTreeNode;
-    procedure Init;
+    TVNodeMakeExe: TTreeNode;
+    TVNodeDebugger: TTreeNode;
+    procedure Init; //Check for config errors, find and show alternatives
     property IdleConnected: boolean read FIdleConnected write SetIdleConnected;
   end;
 
@@ -164,10 +190,15 @@
 procedure SetupFPCSrcDir(FPCVer: string);
 
 function CheckMakeExeQuality(AFilename: string;
-  out Note: string): TSDFilenameQuality;
-function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList;
-procedure SetupMakeExe;
+  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid make executable
+function SearchMakeExeCandidates(StopIfFits: boolean): TObjectList; //Search make candidates and add them to the list, including quality level
+procedure SetupMakeExe; //Checks if the make specified in user's options (if any) is ok. If not, search for and set a valid one if possible
 
+function CheckDebuggerQuality(AFilename: string;
+  out Note: string): TSDFilenameQuality; // Checks a given file to see if it is a valid debugger (only gdb supported for now)
+function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList; //Search debugger candidates and add them to list, including quality level
+procedure SetupDebugger; //Checks if the debugger specified in user's option (if any) is ok. If not, search for and set a valid one if possible
+
 function GetValueFromPrimaryConfig(OptionFilename, Path: string): string;
 function GetValueFromSecondaryConfig(OptionFilename, Path: string): string;
 function GetValueFromIDEConfig(OptionFilename, Path: string): string;
@@ -383,7 +414,7 @@
     if EnvironmentOptions.LazarusDirectory<>Dir then
       dbgout(' => "',Dir,'"');
     dbgout(' is invalid (Error: ',Note,')');
-    debugln(' Searching a proper one ...');
+    debugln(' Searching for a proper one ...');
   end else begin
     debugln(' Searching ...');
   end;
@@ -565,7 +596,7 @@
 
     // check $(LazarusDir)\fpc\bin\i386-win32\fpc.exe
     if CheckFile(SetDirSeparators('$(LazarusDir)/fpc/bin/$(TargetCPU)-$(TargetOS)/')+ShortCompFile,Result)
-    then exit;
+      then exit;
 
     // check common directories
     Files:=TStringList.Create;
@@ -577,8 +608,8 @@
       Files.Free;
     end;
 
+    // Windows-only locations:
     if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
-      // Windows has some special places
       SysDrive:=GetEnvironmentVariableUTF8('SYSTEMDRIVE');
       if SysDrive='' then SysDrive:='C:';
       SysDrive:=AppendPathDelim(SysDrive);
@@ -616,7 +647,7 @@
     if EnvironmentOptions.CompilerFilename<>Filename then
       dbgout(' => "',Filename,'"');
     dbgout(' is invalid (Error: ',Note,')');
-    debugln(' Searching a proper one ...');
+    debugln(' Searching for a proper one ...');
   end else begin
     debugln(' Searching compiler ...');
   end;
@@ -822,7 +853,7 @@
     if EnvironmentOptions.FPCSourceDirectory<>Dir then
       dbgout(' => "',Dir,'"');
     dbgout(' is invalid (Error: ',Note,')');
-    debugln(' Searching a proper one ...');
+    debugln(' Searching for a proper one ...');
   end else begin
     debugln(' Searching ...');
   end;
@@ -842,6 +873,165 @@
   end;
 end;
 
+function CheckDebuggerQuality(AFilename: string; out Note: string
+  ): TSDFilenameQuality;
+begin
+  Result:=sddqInvalid;
+  AFilename:=TrimFilename(AFilename);
+  if not FileExistsCached(AFilename) then
+  begin
+    Note:=lisFileNotFound4;
+    exit;
+  end;
+  if DirPathExistsCached(AFilename) then
+  begin
+    Note:=lisFileIsDirectory;
+    exit;
+  end;
+  if not FileIsExecutableCached(AFilename) then
+  begin
+    Note:=lisFileIsNotAnExecutable;
+    exit;
+  end;
+
+  { We could call gdb and parse the output looking for something like
+  GNU gdb, but that may be going too far. }
+  Note:=lisOk;
+  Result:=sddqCompatible;
+end;
+
+function SearchDebuggerCandidates(StopIfFits: boolean): TObjectList;
+
+  function CheckFile(AFilename: string; var List: TObjectList): boolean;
+  var
+    Item: TSDFileInfo;
+    RealFilename: String;
+  begin
+    Result:=false;
+    if AFilename='' then exit;
+    DoDirSeparators(AFilename);
+    // check if already checked
+    if CaptionInSDFileList(AFilename,List) then exit;
+    EnvironmentOptions.DebuggerFilename:=AFilename;
+    RealFilename:=EnvironmentOptions.GetParsedDebuggerFilename;
+    debugln(['SearchDebuggerCandidates Value=',AFilename,' File=',RealFilename]);
+    if RealFilename='' then exit;
+    // check if exists
+    if not FileExistsCached(RealFilename) then exit;
+    // add to list and check quality
+    Item:=TSDFileInfo.Create;
+    Item.Filename:=RealFilename;
+    Item.Quality:=CheckDebuggerQuality(RealFilename,Item.Note);
+    Item.Caption:=AFilename;
+    if List=nil then
+      List:=TObjectList.create(true);
+    List.Add(Item);
+    Result:=(Item.Quality=sddqCompatible) and StopIfFits;
+  end;
+const
+  DebuggerFileName='gdb'; //For Windows, .exe will be appended
+var
+  OldDebuggerFilename: String;
+  AFilename: String;
+  Files: TStringList;
+  i: Integer;
+begin
+  Result:=nil;
+
+  OldDebuggerFilename:=EnvironmentOptions.DebuggerFilename;
+  try
+    // check current setting
+    if CheckFile(EnvironmentOptions.DebuggerFilename,Result) then exit;
+
+    // check the primary options
+    AFilename:=GetValueFromPrimaryConfig(EnvOptsConfFileName,
+                                    'EnvironmentOptions/DebuggerFilename/Value');
+    if CheckFile(AFilename,Result) then exit;
+
+    // check the secondary options
+    AFilename:=GetValueFromSecondaryConfig(EnvOptsConfFileName,
+                                    'EnvironmentOptions/DebuggerFilename/Value');
+    if CheckFile(AFilename,Result) then exit;
+
+    // The next 2 locations are locations used by older and newer versions of the Windows installers
+    // If other platform installers follow the same strategy, this can be useful.
+    // Chances of this are low (gdb is generally installed in the path on Unixy systems), but it can't hurt...
+    // and it can be useful for cross compiling/custom setups.
+
+    // Check new installation location: $(LazarusDir)\mingw\$(TargetCPU)-$(TargetOS)\bin\gdb.exe
+    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/$(TargetCPU)-$(TargetOS)/bin/'+DebuggerFileName+GetExecutableExt),Result)
+      then exit;
+
+    // Older Lazarus installers did not use macros for their debuggers: there was only one debugger
+    // Check old installation location: $(LazarusDir)\mingw\bin\gdb.exe
+    if CheckFile(SetDirSeparators('$(LazarusDir)/mingw/bin/'+DebuggerFileName+GetExecutableExt),Result)
+      then exit;
+
+    // Windows-only locations:
+    if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
+      // check for debugger in fpc.exe directory - could be a lucky shot
+      if CheckFile(SetDirSeparators('$Path($(CompPath))/'+DebuggerFileName+GetExecutableExt),Result)
+        then exit;
+    end;
+
+    // check history
+    Files:=EnvironmentOptions.DebuggerFileHistory;
+    if Files<>nil then
+      for i:=0 to Files.Count-1 do
+        if CheckFile(Files[i],Result) then exit;
+
+    // check PATH
+    AFilename:=DebuggerFileName;
+    AFilename+=GetExecutableExt;
+    if CheckFile(FindDefaultExecutablePath(AFilename),Result) then exit;
+
+    // There are no common directories apart from the PATH
+    // where gdb would be installed. Otherwise we could do something similar as
+    // in SearchMakeExeCandidates.
+  finally
+    EnvironmentOptions.DebuggerFilename:=OldDebuggerFilename;
+  end;
+end;
+
+procedure SetupDebugger;
+var
+  Note: string;
+  Filename: String;
+  Quality: TSDFilenameQuality;
+  BestDir: TSDFileInfo;
+  List: TObjectList;
+begin
+  Filename:=EnvironmentOptions.GetParsedDebuggerFilename;
+  Quality:=CheckDebuggerQuality(Filename,Note);
+  if Quality<>sddqInvalid then exit;
+  // bad debugger
+  dbgout('SetupDebugger:');
+  if EnvironmentOptions.DebuggerFilename<>'' then
+  begin
+    dbgout(' The "gdb" executable "',EnvironmentOptions.DebuggerFilename,'"');
+    if EnvironmentOptions.DebuggerFilename<>Filename then
+      dbgout(' => "',Filename,'"');
+    dbgout(' is invalid (Error: ',Note,')');
+    debugln(' Searching for a proper one ...');
+  end else begin
+    debugln(' Searching "gdb" ...');
+  end;
+  List:=SearchDebuggerCandidates(true);
+  try
+    BestDir:=nil;
+    if List<>nil then
+      BestDir:=TSDFileInfo(List[List.Count-1]);
+    if (BestDir=nil) or (BestDir.Quality=sddqInvalid) then begin
+      debugln(['SetupDebugger: no proper "gdb" found.']);
+      exit;
+    end;
+    EnvironmentOptions.DebuggerFilename:=BestDir.Filename;
+    debugln(['SetupDebugger: using ',EnvironmentOptions.DebuggerFilename]);
+  finally
+    List.Free;
+  end;
+end;
+
 function CheckMakeExeQuality(AFilename: string; out Note: string
   ): TSDFilenameQuality;
 begin
@@ -863,14 +1053,17 @@
     exit;
   end;
 
+  // Windows-only locations:
   if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
-    // under Windows the make.exe is in the same directory as fpc.exe
+    // under Windows, make.exe is in the same directory as fpc.exe
     if not FileExistsCached(ExtractFilePath(AFilename)+'fpc.exe') then begin
-      Note:='There is no fpc.exe in the directory of the '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the fpc compiler.';
+      Note:='There is no fpc.exe in the directory of '+ExtractFilename(AFilename)+'. Usually the make executable is installed together with the FPC compiler.';
       Result:=sddqIncomplete;
+      exit;
     end;
   end;
 
+  Note:=lisOK;
   Result:=sddqCompatible;
 end;
 
@@ -926,6 +1119,7 @@
                                     'EnvironmentOptions/MakeFilename/Value');
     if CheckFile(AFilename,Result) then exit;
 
+    // Windows-only locations:
     if (GetDefaultSrcOSForTargetOS(GetCompiledTargetOS)='win') then begin
       // check make in fpc.exe directory
       if CheckFile(SetDirSeparators('$Path($(CompPath))/make.exe'),Result)
@@ -980,7 +1174,7 @@
     if EnvironmentOptions.MakeFilename<>Filename then
       dbgout(' => "',Filename,'"');
     dbgout(' is invalid (Error: ',Note,')');
-    debugln(' Searching a proper one ...');
+    debugln(' Searching for a proper one ...');
   end else begin
     debugln(' Searching "make" ...');
   end;
@@ -1098,6 +1292,8 @@
   LazarusTabSheet.Caption:='Lazarus';
   CompilerTabSheet.Caption:=lisCompiler;
   FPCSourcesTabSheet.Caption:=lisFPCSources;
+  MakeExeTabSheet.Caption:='make';
+  DebuggerTabSheet.Caption:=lisDebugger;
 
   FHeadGraphic:=TPortableNetworkGraphic.Create;
   FHeadGraphic.LoadFromLazarusResource('ide_icon48x48');
@@ -1105,6 +1301,8 @@
   TVNodeLazarus:=PropertiesTreeView.Items.Add(nil,LazarusTabSheet.Caption);
   TVNodeCompiler:=PropertiesTreeView.Items.Add(nil,CompilerTabSheet.Caption);
   TVNodeFPCSources:=PropertiesTreeView.Items.Add(nil,FPCSourcesTabSheet.Caption);
+  TVNodeMakeExe:=PropertiesTreeView.Items.Add(nil,MakeExeTabSheet.Caption);
+  TVNodeDebugger:=PropertiesTreeView.Items.Add(nil,DebuggerTabSheet.Caption);
   ImgIDError := ImageList1.AddLazarusResource('state_error');
   ImgIDWarning := ImageList1.AddLazarusResource('state_warning');
 
@@ -1122,6 +1320,15 @@
   FPCSrcDirLabel.Caption:=Format(
     lisTheSourcesOfTheFreePascalPackagesAreRequiredForBro, [SetDirSeparators('rtl'
     +'/linux/system.pp')]);
+
+  MakeExeBrowseButton.Caption:=lisPathEditBrowse;
+  MakeExeLabel.Caption:=Format(
+    lisTheMakeExecutableTypicallyHasTheName, ['make'+GetExecutableExt('')]);
+
+  DebuggerBrowseButton.Caption:=lisPathEditBrowse;
+  DebuggerLabel.Caption:=Format(
+    lisTheDebuggerExecutableTypicallyHasTheName, ['gdb'+GetExecutableExt('')]);
+
 end;
 
 procedure TInitialSetupDialog.CompilerComboBoxChange(Sender: TObject);
@@ -1129,6 +1336,35 @@
   UpdateCompilerNote;
 end;
 
+procedure TInitialSetupDialog.DebuggerBrowseButtonClick(Sender: TObject);
+var
+  Filename: String;
+  Dlg: TOpenDialog;
+  Filter: String;
+begin
+  Dlg:=TOpenDialog.Create(nil);
+  try
+    Filename:='gdb'+GetExecutableExt;
+    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
+    Dlg.Options:=Dlg.Options+[ofFileMustExist];
+    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
+    if ExtractFileExt(Filename)<>'' then
+      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
+    Dlg.Filter:=Filter;
+    if not Dlg.Execute then exit;
+    Filename:=Dlg.FileName;
+  finally
+    Dlg.Free;
+  end;
+  DebuggerComboBox.Text:=Filename;
+  UpdateDebuggerNote;
+end;
+
+procedure TInitialSetupDialog.DebuggerComboBoxChange(Sender: TObject);
+begin
+  UpdateDebuggerNote;
+end;
+
 procedure TInitialSetupDialog.CompilerBrowseButtonClick(Sender: TObject);
 var
   Filename: String;
@@ -1193,6 +1429,35 @@
   UpdateLazDirNote;
 end;
 
+procedure TInitialSetupDialog.MakeExeBrowseButtonClick(Sender: TObject);
+var
+  Filename: String;
+  Dlg: TOpenDialog;
+  Filter: String;
+begin
+  Dlg:=TOpenDialog.Create(nil);
+  try
+    Filename:='make'+GetExecutableExt;
+    Dlg.Title:=Format(lisSelectPathTo, [Filename]);
+    Dlg.Options:=Dlg.Options+[ofFileMustExist];
+    Filter:=dlgAllFiles+'|'+GetAllFilesMask;
+    if ExtractFileExt(Filename)<>'' then
+      Filter:=lisExecutable+'|*'+ExtractFileExt(Filename)+'|'+Filter;
+    Dlg.Filter:=Filter;
+    if not Dlg.Execute then exit;
+    Filename:=Dlg.FileName;
+  finally
+    Dlg.Free;
+  end;
+  MakeExeComboBox.Text:=Filename;
+  UpdateMakeExeNote;
+end;
+
+procedure TInitialSetupDialog.MakeExeComboBoxChange(Sender: TObject);
+begin
+  UpdateMakeExeNote;
+end;
+
 procedure TInitialSetupDialog.PropertiesPageControlChange(Sender: TObject);
 var
   s: String;
@@ -1219,13 +1484,17 @@
   s: String;
   MsgResult: TModalResult;
 begin
-  Node:=FirstErrorNode;
+  Node:=FirstErrorNode(false);
   if Node=TVNodeLazarus then
     s:=lisWithoutAProperLazarusDirectoryYouWillGetALotOfWarn
   else if Node=TVNodeCompiler then
     s:=lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW
   else if Node=TVNodeFPCSources then
-    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio;
+    s:=lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio
+  else if Node=TVNodeMakeExe then
+    s:=lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp
+  else if Node=TVNodeDebugger then
+    s:=lisWithoutAProperDebuggerDebuggingWillBeDisappointing;
   if s<>'' then begin
     MsgResult:=MessageDlg(lisCCOWarningCaption, s, mtWarning, [mbIgnore,
       mbCancel], 0);
@@ -1241,9 +1510,13 @@
   s:=FPCSrcDirComboBox.Text;
   if s<>'' then
     EnvironmentOptions.FPCSourceDirectory:=s;
+  s:=MakeExeComboBox.Text;
+  if s<>'' then
+    EnvironmentOptions.MakeFilename:=s;
+  s:=DebuggerComboBox.Text;
+  if s<>'' then
+    EnvironmentOptions.DebuggerFilename:=s;
 
-  SetupMakeExe;
-
   ModalResult:=mrOk;
 end;
 
@@ -1267,6 +1540,12 @@
   end else if fCompilerFilenameChanged then begin
     UpdateFPCSrcDirCandidates;
     UpdateFPCSrcDirNote;
+  end else if fMakeExeFilenameChanged then begin
+    UpdateMakeExeCandidates;
+    UpdateMakeExeNote;
+  end else if fDebuggerFilenameChanged then begin
+    UpdateDebuggerCandidates;
+    UpdateDebuggerNote;
   end else
     IdleConnected:=false;
 end;
@@ -1341,6 +1620,28 @@
   FillComboboxWithFileInfoList(FPCSrcDirComboBox,Dirs);
 end;
 
+procedure TInitialSetupDialog.UpdateMakeExeCandidates;
+var
+  Files: TObjectList;
+begin
+  FLazarusDirChanged:=false;
+  Files:=SearchMakeExeCandidates(false);
+  FreeAndNil(FCandidates[sddtMakeExeFileName]);
+  FCandidates[sddtMakeExeFileName]:=Files;
+  FillComboboxWithFileInfoList(MakeExeComboBox,Files);
+end;
+
+procedure TInitialSetupDialog.UpdateDebuggerCandidates;
+var
+  Files: TObjectList;
+begin
+  FLazarusDirChanged:=false;
+  Files:=SearchDebuggerCandidates(false);
+  FreeAndNil(FCandidates[sddtDebuggerFilename]);
+  FCandidates[sddtDebuggerFilename]:=Files;
+  FillComboboxWithFileInfoList(DebuggerComboBox,Files);
+end;
+
 procedure TInitialSetupDialog.FillComboboxWithFileInfoList(ABox: TComboBox;
   List: TObjectList; ItemIndex: integer);
 var
@@ -1479,8 +1780,78 @@
   TVNodeFPCSources.SelectedIndex:=ImageIndex;
 end;
 
-function TInitialSetupDialog.FirstErrorNode: TTreeNode;
+procedure TInitialSetupDialog.UpdateMakeExeNote;
 var
+  CurCaption: String;
+  Note: string;
+  Quality: TSDFilenameQuality;
+  s: String;
+  ImageIndex: Integer;
+begin
+  if csDestroying in ComponentState then exit;
+  CurCaption:=MakeExeComboBox.Text;
+  EnvironmentOptions.MakeFilename:=CurCaption;
+  if fLastParsedMakeExe=EnvironmentOptions.GetParsedMakeFilename then exit;
+  fLastParsedMakeExe:=EnvironmentOptions.GetParsedMakeFilename;
+  //debugln(['TInitialSetupDialog.UpdateMakeExeNote ',fLastParsedMakeExe]);
+  Quality:=CheckMakeExeQuality(fLastParsedMakeExe,Note);
+
+  case Quality of
+  sddqInvalid: s:=lisError;
+  sddqCompatible: s:='';
+  else s:=lisWarning;
+  end;
+  if EnvironmentOptions.MakeFilename<>EnvironmentOptions.GetParsedMakeFilename
+  then
+    s:=lisFile2+EnvironmentOptions.GetParsedMakeFilename+LineEnding+
+      LineEnding+s;
+  MakeExeMemo.Text:=s+Note;
+
+  ImageIndex:=QualityToImgIndex(Quality);
+  TVNodeMakeExe.ImageIndex:=ImageIndex;
+  TVNodeMakeExe.SelectedIndex:=ImageIndex;
+
+  fMakeExeFilenameChanged:=true;
+  IdleConnected:=true;
+end;
+
+procedure TInitialSetupDialog.UpdateDebuggerNote;
+var
+  CurCaption: String;
+  Note: string;
+  Quality: TSDFilenameQuality;
+  s: String;
+  ImageIndex: Integer;
+begin
+  if csDestroying in ComponentState then exit;
+  CurCaption:=DebuggerComboBox.Text;
+  EnvironmentOptions.DebuggerFilename:=CurCaption;
+  if fLastParsedDebugger=EnvironmentOptions.GetParsedDebuggerFilename then exit;
+  fLastParsedDebugger:=EnvironmentOptions.GetParsedDebuggerFilename;
+  //debugln(['TInitialSetupDialog.UpdateDebuggerNote ',fLastParsedDebugger]);
+  Quality:=CheckDebuggerQuality(fLastParsedDebugger,Note);
+
+  case Quality of
+  sddqInvalid: s:=lisError;
+  sddqCompatible: s:='';
+  else s:=lisWarning;
+  end;
+  if EnvironmentOptions.DebuggerFilename<>EnvironmentOptions.GetParsedDebuggerFilename
+  then
+    s:=lisFile2+EnvironmentOptions.GetParsedDebuggerFilename+LineEnding+
+      LineEnding+s;
+  DebuggerMemo.Text:=s+Note;
+
+  ImageIndex:=QualityToImgIndex(Quality);
+  TVNodeDebugger.ImageIndex:=ImageIndex;
+  TVNodeDebugger.SelectedIndex:=ImageIndex;
+
+  fDebuggerFilenameChanged:=true;
+  IdleConnected:=true;
+end;
+
+function TInitialSetupDialog.FirstErrorNode(IncludeWarnings: boolean): TTreeNode;
+var
   i: Integer;
 begin
   for i:=0 to PropertiesTreeView.Items.TopLvlCount-1 do
@@ -1488,6 +1859,14 @@
     Result:=PropertiesTreeView.Items.TopLvlItems[i];
     if Result.ImageIndex=ImgIDError then exit;
   end;
+  if IncludeWarnings then
+  begin
+    for i:=0 to PropertiesTreeView.Items.TopLvlCount-1 do
+    begin
+      Result:=PropertiesTreeView.Items.TopLvlItems[i];
+      if Result.ImageIndex=ImgIDWarning then exit;
+    end;
+  end;
   Result:=nil;
 end;
 
@@ -1518,6 +1897,8 @@
     Result:=-1
   else if Quality=sddqWrongMinorVersion then
     Result:=ImgIDWarning
+  else if Quality=sddqIncomplete then
+    Result:=ImgIDWarning
   else
     Result:=ImgIDError;
 end;
@@ -1568,9 +1949,38 @@
   fLastParsedFPCSrcDir:='. .';
   UpdateFPCSrcDirNote;
 
-  // select first error
-  Node:=FirstErrorNode;
+  // Make executable
+  UpdateMakeExeCandidates;
+  if (not FileExistsCached(EnvironmentOptions.Filename)) then
+  begin
+    // first start => choose first best candidate
+    Candidate:=GetFirstCandidate(FCandidates[sddtMakeExeFilename]);
+    if Candidate<>nil then
+      EnvironmentOptions.MakeFilename:=Candidate.Caption;
+  end;
+  MakeExeComboBox.Text:=EnvironmentOptions.MakeFilename;
+  fLastParsedMakeExe:='. .';
+  UpdateMakeExeNote;
+
+  // Debugger
+  UpdateDebuggerCandidates;
+  if (not FileExistsCached(EnvironmentOptions.Filename)) then
+  begin
+    // first start => choose first best candidate
+    Candidate:=GetFirstCandidate(FCandidates[sddtDebuggerFilename]);
+    if Candidate<>nil then
+      EnvironmentOptions.DebuggerFilename:=Candidate.Caption;
+  end;
+  DebuggerComboBox.Text:=EnvironmentOptions.DebuggerFilename;
+  fLastParsedDebugger:='. .';
+  UpdateDebuggerNote;
+
+  // select first error...
+  Node:=FirstErrorNode(false);
+  // ... or warning if no errors found
   if Node=nil then
+    Node:=FirstErrorNode(true);
+  if Node=nil then
     Node:=TVNodeLazarus;
   PropertiesTreeView.Selected:=Node;
 end;
Index: ide/lazarusidestrconsts.pas
===================================================================
--- ide/lazarusidestrconsts.pas	(revision 38091)
+++ ide/lazarusidestrconsts.pas	(working copy)
@@ -2008,6 +2008,7 @@
   dlgCOLibraries = 'Libraries (-Fl):';
   dlgCODebugPath = 'Debugger path addition (none):';
   lisCompiler = 'Compiler';
+  lisDebugger = 'Debugger';
   lisToFPCPath = 'Path:';
   lisCOSkipCallingCompiler = 'Skip calling compiler';
   lisCOAmbiguousAdditionalCompilerConfigFile = 'Ambiguous additional compiler '
@@ -5437,6 +5438,10 @@
     +'Lazarus directory you will get a lot of warnings.';
   lisWithoutAProperCompilerTheCodeBrowsingAndCompilingW = 'Without a proper '
     +'compiler the code browsing and compiling will be disappointing.';
+  lisWithoutAProperDebuggerDebuggingWillBeDisappointing = 'Without a proper '
+    +'debugger, debugging will be disappointing.';
+  lisWithoutAProperMakeExecutableTheCodeBrowsingAndComp = 'Without a proper '
+    +'make executable the code browsing and compiling will be disappointing.';
   lisWithoutTheProperFPCSourcesCodeBrowsingAndCompletio = 'Without the proper '
     +'FPC sources code browsing and completion will be very limited.';
   lisTheLazarusDirectoryContainsTheSourcesOfTheIDEAndTh = 'The Lazarus '
@@ -5446,6 +5451,11 @@
   lisTheFreePascalCompilerExecutableTypicallyHasTheName = 'The Free Pascal '
     +'compiler executable typically has the name "%s". You can also use the '
     +'target specific compiler like "%s". Please give the full file path.';
+  lisTheMakeExecutableTypicallyHasTheName = 'The make executable typically '
+    +'has the name "%s". Please give the full file path.';
+  lisTheDebuggerExecutableTypicallyHasTheName = 'The debugger executable '
+    +'typically has the name "%s". Pleae give the full file path. '
+    +'A useful setting on Windows systems is: $(LazarusDir)\mingw\bin\$(TargetCPU)-$(TargetOS)\gdb.exe';
   lisFoundVersionExpected = 'Found version %s, expected %s';
   lisInvalidVersionIn = 'invalid version in %s';
   lisWrongVersionIn = 'wrong version in %s: %s';

Mattias Gaertner

2012-07-31 13:10

manager   ~0061317

Thanks.

Reinier Olislagers

2012-07-31 13:23

developer   ~0061318

Thanks for the implementation & improvements, Mattias!

Issue History

Date Modified Username Field Change
2012-07-31 12:02 Reinier Olislagers New Issue
2012-07-31 12:02 Reinier Olislagers File Added: initial_checkdebugger.diff
2012-07-31 12:02 Reinier Olislagers Widgetset => Win32/Win64
2012-07-31 12:11 Reinier Olislagers Note Added: 0061315
2012-07-31 12:11 Reinier Olislagers Tag Attached: debugger
2012-07-31 12:11 Reinier Olislagers Tag Attached: gdb
2012-07-31 12:11 Reinier Olislagers Tag Attached: make
2012-07-31 12:11 Reinier Olislagers Tag Attached: check
2012-07-31 12:11 Reinier Olislagers Tag Attached: setup
2012-07-31 12:12 Reinier Olislagers File Added: initial_checkdebugger2.diff
2012-07-31 12:51 Reinier Olislagers Note Added: 0061316
2012-07-31 12:52 Reinier Olislagers File Added: initial_checkdebugger3.diff
2012-07-31 13:10 Mattias Gaertner LazTarget => -
2012-07-31 13:10 Mattias Gaertner Note Added: 0061317
2012-07-31 13:10 Mattias Gaertner Assigned To => Mattias Gaertner
2012-07-31 13:10 Mattias Gaertner Status new => resolved
2012-07-31 13:10 Mattias Gaertner Resolution open => fixed
2012-07-31 13:23 Reinier Olislagers Status resolved => closed
2012-07-31 13:23 Reinier Olislagers Note Added: 0061318