mirror of
https://gitlab.com/freepascal.org/lazarus/lazarus.git
synced 2025-08-27 16:20:35 +02:00
IDE: renamed circle detection with cycle detection
git-svn-id: trunk@34541 -
This commit is contained in:
parent
51a5483ed9
commit
48657d7019
@ -318,7 +318,7 @@ begin
|
|||||||
ReferenceControl,ReferenceSide,CheckPosition))
|
ReferenceControl,ReferenceSide,CheckPosition))
|
||||||
then begin
|
then begin
|
||||||
if MessageDlg(lisCCOWarningCaption,
|
if MessageDlg(lisCCOWarningCaption,
|
||||||
lisThisWillCreateACircle, mtWarning, [mbIgnore, mbCancel], 0)<>
|
lisThisWillCreateACycle, mtWarning, [mbIgnore, mbCancel], 0)<>
|
||||||
mrIgnore
|
mrIgnore
|
||||||
then begin
|
then begin
|
||||||
Refresh(false);
|
Refresh(false);
|
||||||
@ -538,7 +538,7 @@ begin
|
|||||||
ReferenceControl,ReferenceSide,CheckPosition))
|
ReferenceControl,ReferenceSide,CheckPosition))
|
||||||
then begin
|
then begin
|
||||||
if MessageDlg(lisCCOWarningCaption,
|
if MessageDlg(lisCCOWarningCaption,
|
||||||
lisThisWillCreateACircle, mtWarning, [mbIgnore, mbCancel], 0)<>
|
lisThisWillCreateACycle, mtWarning, [mbIgnore, mbCancel], 0)<>
|
||||||
mrIgnore
|
mrIgnore
|
||||||
then begin
|
then begin
|
||||||
Refresh(false);
|
Refresh(false);
|
||||||
@ -649,7 +649,7 @@ begin
|
|||||||
ReferenceControl,ReferenceSide,CheckPosition))
|
ReferenceControl,ReferenceSide,CheckPosition))
|
||||||
then begin
|
then begin
|
||||||
if MessageDlg(lisCCOWarningCaption,
|
if MessageDlg(lisCCOWarningCaption,
|
||||||
lisThisWillCreateACircle, mtWarning, [mbIgnore, mbCancel], 0)<>
|
lisThisWillCreateACycle, mtWarning, [mbIgnore, mbCancel], 0)<>
|
||||||
mrIgnore
|
mrIgnore
|
||||||
then begin
|
then begin
|
||||||
Refresh(false);
|
Refresh(false);
|
||||||
|
@ -1975,11 +1975,11 @@ var
|
|||||||
//DebugLn(['AddComponent ',dbgsName(NewComponentClass)]);
|
//DebugLn(['AddComponent ',dbgsName(NewComponentClass)]);
|
||||||
if NewComponentClass = nil then exit;
|
if NewComponentClass = nil then exit;
|
||||||
|
|
||||||
// check circles
|
// check cycles
|
||||||
if TheFormEditor.ClassDependsOnComponent(NewComponentClass, LookupRoot) then
|
if TheFormEditor.ClassDependsOnComponent(NewComponentClass, LookupRoot) then
|
||||||
begin
|
begin
|
||||||
IDEMessageDialog(lisInvalidCircle,
|
IDEMessageDialog(lisInvalidCycle,
|
||||||
Format(lisIsAThisCircleDependencyIsNotAllowed, [dbgsName(LookupRoot),
|
Format(lisIsAThisCycleDependencyIsNotAllowed, [dbgsName(LookupRoot),
|
||||||
dbgsName(NewComponentClass), #13]),
|
dbgsName(NewComponentClass), #13]),
|
||||||
mtError,[mbOk],'');
|
mtError,[mbOk],'');
|
||||||
exit;
|
exit;
|
||||||
|
@ -3711,7 +3711,7 @@ begin
|
|||||||
if ParsedStamp[Option]<>CompilerParseStamp then begin
|
if ParsedStamp[Option]<>CompilerParseStamp then begin
|
||||||
if Parsing[Option] then begin
|
if Parsing[Option] then begin
|
||||||
DebugLn('TParsedCompilerOptions.GetParsedValue Circle in Options: ',EnumToStr(Option),' Unparsed="',UnparsedValues[Option],'"');
|
DebugLn('TParsedCompilerOptions.GetParsedValue Circle in Options: ',EnumToStr(Option),' Unparsed="',UnparsedValues[Option],'"');
|
||||||
ParsedError(Option, lisCircleInMacros);
|
ParsedError(Option, lisCycleInMacros);
|
||||||
exit('');
|
exit('');
|
||||||
end;
|
end;
|
||||||
Parsing[Option]:=true;
|
Parsing[Option]:=true;
|
||||||
|
@ -3647,15 +3647,15 @@ resourcestring
|
|||||||
+'Project Inspector.';
|
+'Project Inspector.';
|
||||||
lisPkgMangARequiredPackagesWasNotFound = 'A required packages was not '
|
lisPkgMangARequiredPackagesWasNotFound = 'A required packages was not '
|
||||||
+'found. See package graph.';
|
+'found. See package graph.';
|
||||||
lisPkgMangCircleInPackageDependencies = 'Circle in package dependencies';
|
lisPkgMangCycleInPackageDependencies = 'Cycle in package dependencies';
|
||||||
lisPkgMangThePackageIsCompiledAutomaticallyAndItsOutputDirec = 'The package '
|
lisPkgMangThePackageIsCompiledAutomaticallyAndItsOutputDirec = 'The package '
|
||||||
+'%s is compiled automatically and its output directory is "%s", which is '
|
+'%s is compiled automatically and its output directory is "%s", which is '
|
||||||
+'in the default unit search path of the compiler. The package uses other '
|
+'in the default unit search path of the compiler. The package uses other '
|
||||||
+'packages which also uses the default unit search of the compiler. This '
|
+'packages which also uses the default unit search of the compiler. This '
|
||||||
+'creates a circle.%sYou can fix this issue%sby removing the path from '
|
+'creates a cycle.%sYou can fix this issue%sby removing the path from '
|
||||||
+'your compiler config (e.g. fpc.cfg)%sor by disabling the auto update of '
|
+'your compiler config (e.g. fpc.cfg)%sor by disabling the auto update of '
|
||||||
+'this package%sor by removing dependencies.';
|
+'this package%sor by removing dependencies.';
|
||||||
lisPkgMangThereIsACircleInTheRequiredPackages = 'There is a circle in the '
|
lisPkgMangThereIsACycleInTheRequiredPackages = 'There is a cycle in the '
|
||||||
+'required packages. See package graph.';
|
+'required packages. See package graph.';
|
||||||
lisPkgMangThereAreTwoUnitsWithTheSameName1From2From = 'There are two units '
|
lisPkgMangThereAreTwoUnitsWithTheSameName1From2From = 'There are two units '
|
||||||
+'with the same name:%s%s1. %s%s%s from %s%s2. %s%s%s from %s%s%s';
|
+'with the same name:%s%s1. %s%s%s from %s%s2. %s%s%s from %s%s%s';
|
||||||
@ -3926,7 +3926,7 @@ resourcestring
|
|||||||
lisA2PInvalidClassName = 'Invalid Class Name';
|
lisA2PInvalidClassName = 'Invalid Class Name';
|
||||||
lisA2PTheClassNameIsNotAValidPascalIdentifier = 'The class name %s%s%s is '
|
lisA2PTheClassNameIsNotAValidPascalIdentifier = 'The class name %s%s%s is '
|
||||||
+'not a valid pascal identifier.';
|
+'not a valid pascal identifier.';
|
||||||
lisA2PInvalidCircle = 'Invalid Circle';
|
lisA2PInvalidCycle = 'Invalid Cycle';
|
||||||
lisA2PTheClassNameAndAncestorTypeAreTheSame = 'The class name %s%s%s and '
|
lisA2PTheClassNameAndAncestorTypeAreTheSame = 'The class name %s%s%s and '
|
||||||
+'ancestor type %s%s%s are the same.';
|
+'ancestor type %s%s%s are the same.';
|
||||||
lisA2PAmbiguousAncestorType = 'Ambiguous Ancestor Type';
|
lisA2PAmbiguousAncestorType = 'Ambiguous Ancestor Type';
|
||||||
@ -4491,7 +4491,7 @@ resourcestring
|
|||||||
lisLeftGroupBoxCaption = 'Left anchoring';
|
lisLeftGroupBoxCaption = 'Left anchoring';
|
||||||
lisBottomGroupBoxCaption = 'Bottom anchoring';
|
lisBottomGroupBoxCaption = 'Bottom anchoring';
|
||||||
lisUnableToSetAnchorSideControl = 'Unable to set AnchorSide Control';
|
lisUnableToSetAnchorSideControl = 'Unable to set AnchorSide Control';
|
||||||
lisThisWillCreateACircle = 'This will create a circle.';
|
lisThisWillCreateACycle = 'This will create a cycle.';
|
||||||
lisAnchorEditorNoControlSelected = 'Anchor Editor - no control selected';
|
lisAnchorEditorNoControlSelected = 'Anchor Editor - no control selected';
|
||||||
lisAnchorsOfSelectedControls = 'Anchors of selected controls';
|
lisAnchorsOfSelectedControls = 'Anchors of selected controls';
|
||||||
lisDebugOptionsFrmAdditionalSearchPath = 'Additional search path';
|
lisDebugOptionsFrmAdditionalSearchPath = 'Additional search path';
|
||||||
@ -4803,8 +4803,8 @@ resourcestring
|
|||||||
lisPWOpenRecentProject = 'Open Recent Project';
|
lisPWOpenRecentProject = 'Open Recent Project';
|
||||||
lisPWViewExampleProjects = 'View Example Projects';
|
lisPWViewExampleProjects = 'View Example Projects';
|
||||||
lisPWConvertProject = 'Convert Delphi Project';
|
lisPWConvertProject = 'Convert Delphi Project';
|
||||||
lisInvalidCircle = 'Invalid circle';
|
lisInvalidCycle = 'Invalid cycle';
|
||||||
lisIsAThisCircleDependencyIsNotAllowed = '%s is a %s.%sThis circle '
|
lisIsAThisCycleDependencyIsNotAllowed = '%s is a %s.%sThis cycle '
|
||||||
+'dependency is not allowed.';
|
+'dependency is not allowed.';
|
||||||
lisTheComponentCanNotBeDeletedBecauseItIsNotOwnedBy = 'The component %s can '
|
lisTheComponentCanNotBeDeletedBecauseItIsNotOwnedBy = 'The component %s can '
|
||||||
+'not be deleted, because it is not owned by %s.';
|
+'not be deleted, because it is not owned by %s.';
|
||||||
@ -5279,7 +5279,7 @@ resourcestring
|
|||||||
lisPEDirectories = 'Directories';
|
lisPEDirectories = 'Directories';
|
||||||
lisSelectAnotherLCLWidgetSetMacroLCLWidgetType = 'Select another LCL widget '
|
lisSelectAnotherLCLWidgetSetMacroLCLWidgetType = 'Select another LCL widget '
|
||||||
+'set (macro LCLWidgetType)';
|
+'set (macro LCLWidgetType)';
|
||||||
lisCircleInMacros = 'Circle in macros';
|
lisCycleInMacros = 'Cycle in macros';
|
||||||
|
|
||||||
// Uses Unit dialog
|
// Uses Unit dialog
|
||||||
dlgAlreadyUsesAllOtherUnits = '"%s" already uses all the units in this project';
|
dlgAlreadyUsesAllOtherUnits = '"%s" already uses all the units in this project';
|
||||||
|
@ -861,7 +861,7 @@ begin
|
|||||||
|
|
||||||
// check classname<>ancestortype
|
// check classname<>ancestortype
|
||||||
if AnsiCompareText(Params.NewClassName,Params.AncestorType)=0 then begin
|
if AnsiCompareText(Params.NewClassName,Params.AncestorType)=0 then begin
|
||||||
IDEMessageDialog(lisA2PInvalidCircle,
|
IDEMessageDialog(lisA2PInvalidCycle,
|
||||||
Format(lisA2PTheClassNameAndAncestorTypeAreTheSame, ['"',
|
Format(lisA2PTheClassNameAndAncestorTypeAreTheSame, ['"',
|
||||||
Params.NewClassName, '"', '"', Params.AncestorType, '"']),
|
Params.NewClassName, '"', '"', Params.AncestorType, '"']),
|
||||||
mtError,[mbCancel]);
|
mtError,[mbCancel]);
|
||||||
|
@ -505,7 +505,7 @@ type
|
|||||||
lpfDestroying, // set during destruction
|
lpfDestroying, // set during destruction
|
||||||
lpfLoading, // set during loading
|
lpfLoading, // set during loading
|
||||||
lpfSkipSaving, // Used by PkgBoss to skip saving
|
lpfSkipSaving, // Used by PkgBoss to skip saving
|
||||||
lpfCircle // Used by the PackageGraph to mark circles
|
lpfCycle // Used by the PackageGraph to mark cycles
|
||||||
);
|
);
|
||||||
TLazPackageFlags = set of TLazPackageFlag;
|
TLazPackageFlags = set of TLazPackageFlag;
|
||||||
|
|
||||||
|
@ -193,9 +193,9 @@ type
|
|||||||
function FindBrokenDependencyPath(APackage: TLazPackage;
|
function FindBrokenDependencyPath(APackage: TLazPackage;
|
||||||
FirstDependency: TPkgDependency): TFPList;
|
FirstDependency: TPkgDependency): TFPList;
|
||||||
function FindAllBrokenDependencies(APackage: TLazPackage;
|
function FindAllBrokenDependencies(APackage: TLazPackage;
|
||||||
FirstDependency: TPkgDependency): TFPList;
|
FirstDependency: TPkgDependency): TFPList;
|
||||||
function FindCircleDependencyPath(APackage: TLazPackage;
|
function FindCycleDependencyPath(APackage: TLazPackage;
|
||||||
FirstDependency: TPkgDependency): TFPList;
|
FirstDependency: TPkgDependency): TFPList;
|
||||||
function FindPkgOutputInFPCSearchPath(APackage: TLazPackage;
|
function FindPkgOutputInFPCSearchPath(APackage: TLazPackage;
|
||||||
FirstDependency: TPkgDependency): TFPList; // find a package with auto compile and output dir is in FPC default search path
|
FirstDependency: TPkgDependency): TFPList; // find a package with auto compile and output dir is in FPC default search path
|
||||||
function FindUnsavedDependencyPath(APackage: TLazPackage;
|
function FindUnsavedDependencyPath(APackage: TLazPackage;
|
||||||
@ -2496,10 +2496,10 @@ begin
|
|||||||
FindBroken(FirstDependency,Result);
|
FindBroken(FirstDependency,Result);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TLazPackageGraph.FindCircleDependencyPath(APackage: TLazPackage;
|
function TLazPackageGraph.FindCycleDependencyPath(APackage: TLazPackage;
|
||||||
FirstDependency: TPkgDependency): TFPList;
|
FirstDependency: TPkgDependency): TFPList;
|
||||||
|
|
||||||
procedure FindCircle(Dependency: TPkgDependency; var PathList: TFPList);
|
procedure FindCycle(Dependency: TPkgDependency; var PathList: TFPList);
|
||||||
var
|
var
|
||||||
RequiredPackage: TLazPackage;
|
RequiredPackage: TLazPackage;
|
||||||
begin
|
begin
|
||||||
@ -2507,22 +2507,22 @@ function TLazPackageGraph.FindCircleDependencyPath(APackage: TLazPackage;
|
|||||||
if Dependency.LoadPackageResult=lprSuccess then begin
|
if Dependency.LoadPackageResult=lprSuccess then begin
|
||||||
// dependency ok
|
// dependency ok
|
||||||
RequiredPackage:=Dependency.RequiredPackage;
|
RequiredPackage:=Dependency.RequiredPackage;
|
||||||
if lpfCircle in RequiredPackage.Flags then begin
|
if lpfCycle in RequiredPackage.Flags then begin
|
||||||
// circle detected
|
// cycle detected
|
||||||
PathList:=TFPList.Create;
|
PathList:=TFPList.Create;
|
||||||
PathList.Add(RequiredPackage);
|
PathList.Add(RequiredPackage);
|
||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
if not (lpfVisited in RequiredPackage.Flags) then begin
|
if not (lpfVisited in RequiredPackage.Flags) then begin
|
||||||
RequiredPackage.Flags:=RequiredPackage.Flags+[lpfVisited,lpfCircle];
|
RequiredPackage.Flags:=RequiredPackage.Flags+[lpfVisited,lpfCycle];
|
||||||
FindCircle(RequiredPackage.FirstRequiredDependency,PathList);
|
FindCycle(RequiredPackage.FirstRequiredDependency,PathList);
|
||||||
if PathList<>nil then begin
|
if PathList<>nil then begin
|
||||||
// circle detected
|
// cycle detected
|
||||||
// -> add current package to list
|
// -> add current package to list
|
||||||
PathList.Insert(0,RequiredPackage);
|
PathList.Insert(0,RequiredPackage);
|
||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
RequiredPackage.Flags:=RequiredPackage.Flags-[lpfCircle];
|
RequiredPackage.Flags:=RequiredPackage.Flags-[lpfCycle];
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
Dependency:=Dependency.NextRequiresDependency;
|
Dependency:=Dependency.NextRequiresDependency;
|
||||||
@ -2535,16 +2535,16 @@ var
|
|||||||
begin
|
begin
|
||||||
Result:=nil;
|
Result:=nil;
|
||||||
if (Count=0) then exit;
|
if (Count=0) then exit;
|
||||||
// mark all packages as not visited and circle free
|
// mark all packages as not visited and cycle free
|
||||||
for i:=FItems.Count-1 downto 0 do begin
|
for i:=FItems.Count-1 downto 0 do begin
|
||||||
Pkg:=TLazPackage(FItems[i]);
|
Pkg:=TLazPackage(FItems[i]);
|
||||||
Pkg.Flags:=Pkg.Flags-[lpfVisited,lpfCircle];
|
Pkg.Flags:=Pkg.Flags-[lpfVisited,lpfCycle];
|
||||||
end;
|
end;
|
||||||
if APackage<>nil then begin
|
if APackage<>nil then begin
|
||||||
APackage.Flags:=APackage.Flags+[lpfVisited];
|
APackage.Flags:=APackage.Flags+[lpfVisited];
|
||||||
FirstDependency:=APackage.FirstRequiredDependency;
|
FirstDependency:=APackage.FirstRequiredDependency;
|
||||||
end;
|
end;
|
||||||
FindCircle(FirstDependency,Result);
|
FindCycle(FirstDependency,Result);
|
||||||
if (Result<>nil) and (APackage<>nil) then
|
if (Result<>nil) and (APackage<>nil) then
|
||||||
Result.Insert(0,APackage);
|
Result.Insert(0,APackage);
|
||||||
end;
|
end;
|
||||||
@ -2572,7 +2572,7 @@ var
|
|||||||
Dir:=ChompPathDelim(CfgCache.UnitPaths[i]);
|
Dir:=ChompPathDelim(CfgCache.UnitPaths[i]);
|
||||||
if CompareFilenames(Dir,OutputDir)=0 then begin
|
if CompareFilenames(Dir,OutputDir)=0 then begin
|
||||||
// this package changes the units in the default FPC search path
|
// this package changes the units in the default FPC search path
|
||||||
// => a circle, because the dependencies use FPC search path too
|
// => a cycle, because the dependencies use FPC search path too
|
||||||
Result:=false;
|
Result:=false;
|
||||||
PathList:=TFPList.Create;
|
PathList:=TFPList.Create;
|
||||||
PathList.Add(Pkg);
|
PathList.Add(Pkg);
|
||||||
@ -2592,7 +2592,7 @@ var
|
|||||||
if CheckPkg(RequiredPackage,PathList) then exit;
|
if CheckPkg(RequiredPackage,PathList) then exit;
|
||||||
CheckDependencyList(RequiredPackage.FirstRequiredDependency,PathList);
|
CheckDependencyList(RequiredPackage.FirstRequiredDependency,PathList);
|
||||||
if PathList<>nil then begin
|
if PathList<>nil then begin
|
||||||
// circle detected
|
// cycle detected
|
||||||
// -> add current package to list
|
// -> add current package to list
|
||||||
PathList.Insert(0,RequiredPackage);
|
PathList.Insert(0,RequiredPackage);
|
||||||
exit;
|
exit;
|
||||||
|
@ -1247,12 +1247,12 @@ begin
|
|||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
// check for circle dependencies
|
// check for cycle dependencies
|
||||||
PathList:=PackageGraph.FindCircleDependencyPath(APackage,FirstDependency);
|
PathList:=PackageGraph.FindCycleDependencyPath(APackage,FirstDependency);
|
||||||
if PathList<>nil then begin
|
if PathList<>nil then begin
|
||||||
DoShowPackageGraphPathList(PathList);
|
DoShowPackageGraphPathList(PathList);
|
||||||
Result:=IDEMessageDialogAb(lisPkgMangCircleInPackageDependencies,
|
Result:=IDEMessageDialogAb(lisPkgMangCycleInPackageDependencies,
|
||||||
lisPkgMangThereIsACircleInTheRequiredPackages,
|
lisPkgMangThereIsACycleInTheRequiredPackages,
|
||||||
mtError,Btns,ShowAbort);
|
mtError,Btns,ShowAbort);
|
||||||
if not ShowAbort then
|
if not ShowAbort then
|
||||||
Result := mrCancel; // User confirmed error, implicitly cancel the action
|
Result := mrCancel; // User confirmed error, implicitly cancel the action
|
||||||
@ -1264,7 +1264,7 @@ begin
|
|||||||
if PathList<>nil then begin
|
if PathList<>nil then begin
|
||||||
ConflictPkg:=TObject(PathList[PathList.Count-1]) as TLazPackage;
|
ConflictPkg:=TObject(PathList[PathList.Count-1]) as TLazPackage;
|
||||||
DoShowPackageGraphPathList(PathList);
|
DoShowPackageGraphPathList(PathList);
|
||||||
Result:=IDEMessageDialogAb(lisPkgMangCircleInPackageDependencies,
|
Result:=IDEMessageDialogAb(lisPkgMangCycleInPackageDependencies,
|
||||||
Format(lisPkgMangThePackageIsCompiledAutomaticallyAndItsOutputDirec, [
|
Format(lisPkgMangThePackageIsCompiledAutomaticallyAndItsOutputDirec, [
|
||||||
ConflictPkg.Name, ConflictPkg.GetOutputDirectory, #13#13, #13, #13,
|
ConflictPkg.Name, ConflictPkg.GetOutputDirectory, #13#13, #13, #13,
|
||||||
#13]),
|
#13]),
|
||||||
|
Loading…
Reference in New Issue
Block a user