mirror of
https://gitlab.com/freepascal.org/lazarus/lazarus.git
synced 2025-09-11 10:39:20 +02:00
IDE: circle detection for macros
git-svn-id: trunk@28626 -
This commit is contained in:
parent
43eaec2e45
commit
e454608274
@ -74,11 +74,15 @@ type
|
|||||||
AMacroFunction: TMacroFunction; TheFlags: TTransferMacroFlags);
|
AMacroFunction: TMacroFunction; TheFlags: TTransferMacroFlags);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
{ TTransferMacroList }
|
||||||
|
|
||||||
TTransferMacroList = class
|
TTransferMacroList = class
|
||||||
private
|
private
|
||||||
fItems: TList; // list of TTransferMacro
|
fItems: TFPList; // list of TTransferMacro
|
||||||
FMarkUnhandledMacros: boolean;
|
FMarkUnhandledMacros: boolean;
|
||||||
|
FMaxUsePerMacro: integer;
|
||||||
fOnSubstitution: TOnSubstitution;
|
fOnSubstitution: TOnSubstitution;
|
||||||
|
fBusy: TStringList; // current working Macros, used for circle detection
|
||||||
function GetItems(Index: integer): TTransferMacro;
|
function GetItems(Index: integer): TTransferMacro;
|
||||||
procedure SetItems(Index: integer; NewMacro: TTransferMacro);
|
procedure SetItems(Index: integer; NewMacro: TTransferMacro);
|
||||||
procedure SetMarkUnhandledMacros(const AValue: boolean);
|
procedure SetMarkUnhandledMacros(const AValue: boolean);
|
||||||
@ -107,7 +111,8 @@ type
|
|||||||
property OnSubstitution: TOnSubstitution
|
property OnSubstitution: TOnSubstitution
|
||||||
read fOnSubstitution write fOnSubstitution;
|
read fOnSubstitution write fOnSubstitution;
|
||||||
property MarkUnhandledMacros: boolean read FMarkUnhandledMacros
|
property MarkUnhandledMacros: boolean read FMarkUnhandledMacros
|
||||||
write SetMarkUnhandledMacros;
|
write SetMarkUnhandledMacros default true;
|
||||||
|
property MaxUsePerMacro: integer read FMaxUsePerMacro write FMaxUsePerMacro default 1;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TLazIDEMacros }
|
{ TLazIDEMacros }
|
||||||
@ -180,8 +185,9 @@ end;
|
|||||||
constructor TTransferMacroList.Create;
|
constructor TTransferMacroList.Create;
|
||||||
begin
|
begin
|
||||||
inherited Create;
|
inherited Create;
|
||||||
fItems:=TList.Create;
|
fItems:=TFPList.Create;
|
||||||
FMarkUnhandledMacros:=true;
|
FMarkUnhandledMacros:=true;
|
||||||
|
FMaxUsePerMacro:=3;
|
||||||
Add(TTransferMacro.Create('Ext', '', lisTMFunctionExtractFileExtension,
|
Add(TTransferMacro.Create('Ext', '', lisTMFunctionExtractFileExtension,
|
||||||
@MF_Ext, []));
|
@MF_Ext, []));
|
||||||
Add(TTransferMacro.Create('Path', '', lisTMFunctionExtractFilePath, @MF_Path,
|
Add(TTransferMacro.Create('Path', '', lisTMFunctionExtractFilePath, @MF_Path,
|
||||||
@ -199,7 +205,8 @@ end;
|
|||||||
destructor TTransferMacroList.Destroy;
|
destructor TTransferMacroList.Destroy;
|
||||||
begin
|
begin
|
||||||
Clear;
|
Clear;
|
||||||
fItems.Free;
|
FreeAndNil(fItems);
|
||||||
|
FreeAndNil(fBusy);
|
||||||
inherited Destroy;
|
inherited Destroy;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -289,6 +296,8 @@ var
|
|||||||
NewStringPos: Integer;
|
NewStringPos: Integer;
|
||||||
sLen: Integer;
|
sLen: Integer;
|
||||||
LoopPos, LoopDepth: integer;
|
LoopPos, LoopDepth: integer;
|
||||||
|
InUse: Integer;
|
||||||
|
i: Integer;
|
||||||
|
|
||||||
function SearchBracketClose(Position:integer): integer;
|
function SearchBracketClose(Position:integer): integer;
|
||||||
var BracketClose:char;
|
var BracketClose:char;
|
||||||
@ -346,18 +355,37 @@ begin
|
|||||||
// Macro function -> substitute macro parameter first
|
// Macro function -> substitute macro parameter first
|
||||||
MacroParam:=copy(MacroStr,length(MacroName)+3,
|
MacroParam:=copy(MacroStr,length(MacroName)+3,
|
||||||
length(MacroStr)-length(MacroName)-3);
|
length(MacroStr)-length(MacroName)-3);
|
||||||
if not SubstituteStr(MacroParam,Data,Depth+1) then begin
|
|
||||||
Result:=false;
|
|
||||||
exit;
|
|
||||||
end;
|
|
||||||
AMacro:=FindByName(MacroName);
|
AMacro:=FindByName(MacroName);
|
||||||
if Assigned(fOnSubstitution) then begin
|
InUse:=0;
|
||||||
fOnSubstitution(AMacro,MacroName,MacroParam,Data,Handled,Abort,Depth+LoopDepth);
|
for i:=0 to fBusy.Count-1 do begin
|
||||||
if Handled then
|
if SysUtils.CompareText(fBusy[i],MacroName)=0 then begin
|
||||||
MacroStr:=MacroParam
|
inc(InUse);
|
||||||
else if Abort then begin
|
if InUse>MaxUsePerMacro then begin
|
||||||
Result:=false;
|
// circle detected
|
||||||
exit;
|
Handled:=true;
|
||||||
|
MacroStr:='<CIRCLE:'+MacroName+'>';
|
||||||
|
break;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
if not Handled then begin
|
||||||
|
try
|
||||||
|
fBusy.Add(MacroName);
|
||||||
|
if not SubstituteStr(MacroParam,Data,Depth+1) then begin
|
||||||
|
Result:=false;
|
||||||
|
exit;
|
||||||
|
end;
|
||||||
|
finally
|
||||||
|
fBusy.Delete(fBusy.Count-1);
|
||||||
|
end;
|
||||||
|
if Assigned(fOnSubstitution) then begin
|
||||||
|
fOnSubstitution(AMacro,MacroName,MacroParam,Data,Handled,Abort,Depth+LoopDepth);
|
||||||
|
if Handled then
|
||||||
|
MacroStr:=MacroParam
|
||||||
|
else if Abort then begin
|
||||||
|
Result:=false;
|
||||||
|
exit;
|
||||||
|
end;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
if (not Handled) and (AMacro<>nil) and (Assigned(AMacro.MacroFunction))
|
if (not Handled) and (AMacro<>nil) and (Assigned(AMacro.MacroFunction))
|
||||||
|
Loading…
Reference in New Issue
Block a user