Turn unit ObjectLists to use generics, move it to Lazutils. Reduce typecasts in TPkgManager by using correct types when possible.

git-svn-id: trunk@62639 -
This commit is contained in:
juha 2020-02-17 12:23:38 +00:00
parent 2c8411425b
commit 0961a5797a
7 changed files with 130 additions and 123 deletions

2
.gitattributes vendored
View File

@ -3439,6 +3439,7 @@ components/lazutils/lcsvutils.pas svneol=native#text/pascal
components/lazutils/lookupstringlist.pas svneol=native#text/pascal
components/lazutils/maps.pp svneol=native#text/pascal
components/lazutils/masks.pas svneol=native#text/pascal
components/lazutils/objectlists.pas svneol=native#text/pascal
components/lazutils/paswstring.pas svneol=native#text/pascal
components/lazutils/stringhashlist.pas svneol=native#text/pascal
components/lazutils/test/TestLazStorageMem.lpi svneol=native#text/plain
@ -7576,7 +7577,6 @@ ide/newdialog.pas svneol=native#text/pascal
ide/newprojectdlg.lfm svneol=native#text/plain
ide/newprojectdlg.pp svneol=native#text/pascal
ide/notifyprocessend.pas svneol=native#text/pascal
ide/objectlists.pas svneol=native#text/pascal
ide/pas2jsmsg.txt svneol=native#text/plain
ide/patheditordlg.lfm svneol=native#text/pascal
ide/patheditordlg.pas svneol=native#text/pascal

View File

@ -1,6 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<CONFIG>
<Package Version="4">
<Package Version="5">
<Name Value="LazUtils"/>
<Type Value="RunAndDesignTime"/>
<BuildMethod Value="Both"/>
@ -17,7 +17,7 @@
<Description Value="Useful units for Lazarus packages."/>
<License Value="Modified LGPL-2"/>
<Version Major="1"/>
<Files Count="102">
<Files Count="103">
<Item1>
<Filename Value="LazLoggerImpl.inc"/>
<Type Value="Include"/>
@ -426,6 +426,10 @@
<Filename Value="lazutf8sysutils.pas"/>
<UnitName Value="LazUTF8SysUtils"/>
</Item102>
<Item103>
<Filename Value="objectlists.pas"/>
<UnitName Value="ObjectLists"/>
</Item103>
</Files>
<LazDoc Paths="../../docs/xml/lazutils"/>
<i18n>

View File

@ -22,7 +22,7 @@ uses
TTFile, TTGLoad, TTInterp, TTLoad, TTMemory, TTObjs, TTProfile, TTRASTER,
TTTables, TTTypes, UTF8Process, HTML2TextRender, Laz_AVL_Tree,
CompWriterPas, LazPasReadUtil, IntegerList, LazVersion, UITypes, GraphType,
LazTracer, LazStringUtils, LazUTF8SysUtils, LazarusPackageIntf;
LazTracer, LazStringUtils, LazUTF8SysUtils, ObjectLists, LazarusPackageIntf;
implementation

View File

@ -26,9 +26,10 @@
***************************************************************************
Author: Mattias Gaertner
Abstract:
Classes to associate objects/pointers with objects/pointers.
Converted to use generics by Juha. Item and Object types can now be defined.
}
unit ObjectLists;
@ -37,48 +38,50 @@ unit ObjectLists;
interface
uses
Classes, SysUtils;
Classes, SysUtils;
type
T2Pointer = record
Item, Associated: Pointer;
end;
P2Pointer = ^T2Pointer;
TObjectArray = class
{ TObjectArray }
generic TObjectArray<TItem, TObj> = class
private
FCapacity: Integer;
FCount: Integer;
FList: P2Pointer;
protected
function Get(Index: Integer): Pointer;
procedure Put(Index: Integer; const AValue: Pointer);
function GetObject(Index: Integer): Pointer;
procedure PutObject(Index: Integer; const AValue: Pointer);
function Get(Index: Integer): TItem;
procedure Put(Index: Integer; const AValue: TItem);
function GetObject(Index: Integer): TObj;
procedure PutObject(Index: Integer; const AValue: TObj);
procedure SetCapacity(const AValue: Integer);
procedure SetCount(const AValue: Integer);
procedure Grow;
procedure Shrink;
public
destructor Destroy; override;
function Add(Item: Pointer): Integer;
function AddObject(Item, Associated: Pointer): Integer;
function Add(Item: TItem): Integer;
function AddObject(Item: TItem; Associated: TObj): Integer;
procedure Clear; virtual;
procedure Delete(Index: Integer);
procedure Exchange(Index1, Index2: Integer);
function First: Pointer;
function IndexOf(Item: Pointer): Integer;
procedure Insert(Index: Integer; Item: Pointer);
procedure InsertObject(Index: Integer; Item, Associated: Pointer);
function Last: Pointer;
function First: TItem;
function IndexOf(Item: TItem): Integer;
procedure Insert(Index: Integer; Item: TItem);
procedure InsertObject(Index: Integer; Item: TItem; Associated: TObj);
function Last: TItem;
procedure Move(CurIndex, NewIndex: Integer);
procedure Assign(SrcList: TList);
function Remove(Item: Pointer): Integer;
function Remove(Item: TItem): Integer;
procedure Pack;
property Capacity: Integer read FCapacity write SetCapacity;
property Count: Integer read FCount write SetCount;
property Items[Index: Integer]: Pointer read Get write Put; default;
property Objects[Index: Integer]: Pointer read GetObject write PutObject;
property Items[Index: Integer]: TItem read Get write Put; default;
property Objects[Index: Integer]: TObj read GetObject write PutObject;
property List: P2Pointer read FList;
end;
@ -86,26 +89,26 @@ implementation
{ TObjectArray }
function TObjectArray.GetObject(Index: Integer): Pointer;
function TObjectArray.Get(Index: Integer): TItem;
begin
Result:=FList[Index].Associated;
Result:=TItem(FList[Index].Item);
end;
procedure TObjectArray.PutObject(Index: Integer; const AValue: Pointer);
begin
FList[Index].Associated:=AValue;
end;
function TObjectArray.Get(Index: Integer): Pointer;
begin
Result:=FList[Index].Item;
end;
procedure TObjectArray.Put(Index: Integer; const AValue: Pointer);
procedure TObjectArray.Put(Index: Integer; const AValue: TItem);
begin
FList[Index].Item:=AValue;
end;
function TObjectArray.GetObject(Index: Integer): TObj;
begin
Result:=TObj(FList[Index].Associated);
end;
procedure TObjectArray.PutObject(Index: Integer; const AValue: TObj);
begin
FList[Index].Associated:=AValue;
end;
procedure TObjectArray.SetCapacity(const AValue: Integer);
begin
if FCapacity=AValue then exit;
@ -138,12 +141,12 @@ begin
inherited Destroy;
end;
function TObjectArray.Add(Item: Pointer): Integer;
function TObjectArray.Add(Item: TItem): Integer;
begin
Result:=AddObject(Item,nil);
end;
function TObjectArray.AddObject(Item, Associated: Pointer): Integer;
function TObjectArray.AddObject(Item: TItem; Associated: TObj): Integer;
begin
if FCount=FCapacity then Grow;
FList[FCount].Item:=Item;
@ -177,26 +180,26 @@ begin
FList[Index2]:=SwapDummy;
end;
function TObjectArray.First: Pointer;
function TObjectArray.First: TItem;
begin
if FCount>0 then
Result:=FList[0].Item
Result:=TItem(FList[0].Item)
else
Result:=nil;
end;
function TObjectArray.IndexOf(Item: Pointer): Integer;
function TObjectArray.IndexOf(Item: TItem): Integer;
begin
Result:=FCount-1;
while (Result>=0) and (FList[Result].Item<>Item) do dec(Result);
while (Result>=0) and (TItem(FList[Result].Item)<>Item) do dec(Result);
end;
procedure TObjectArray.Insert(Index: Integer; Item: Pointer);
procedure TObjectArray.Insert(Index: Integer; Item: TItem);
begin
InsertObject(Index,Item,nil);
end;
procedure TObjectArray.InsertObject(Index: Integer; Item, Associated: Pointer);
procedure TObjectArray.InsertObject(Index: Integer; Item: TItem; Associated: TObj);
begin
if FCount=FCapacity then Grow;
if Index<FCount then
@ -206,10 +209,10 @@ begin
FList[Index].Associated:=Associated;
end;
function TObjectArray.Last: Pointer;
function TObjectArray.Last: TItem;
begin
if FCount>0 then
Result:=FList[FCount-1].Item
Result:=TItem(FList[FCount-1].Item)
else
Result:=nil;
end;
@ -241,7 +244,7 @@ begin
end;
end;
function TObjectArray.Remove(Item: Pointer): Integer;
function TObjectArray.Remove(Item: TItem): Integer;
begin
Result:=IndexOf(Item);
if Result>=0 then Delete(Result);

View File

@ -349,7 +349,6 @@ begin
P.Sources.AddSrc('msgvieweditor.pas');
P.Sources.AddSrc('newdialog.pas');
P.Sources.AddSrc('newprojectdlg.pp');
P.Sources.AddSrc('objectlists.pas');
P.Sources.AddSrc('outputfilter.pas');
P.Sources.AddSrc('patheditordlg.pas');
P.Sources.AddSrc('procedurelist.pas');

View File

@ -1,16 +1,16 @@
<?xml version="1.0" encoding="UTF-8"?>
<CONFIG>
<ProjectOptions>
<Version Value="11"/>
<Version Value="12"/>
<General>
<Flags>
<MainUnitHasUsesSectionForAllUnits Value="False"/>
<MainUnitHasCreateFormStatements Value="False"/>
<MainUnitHasTitleStatement Value="False"/>
<LRSInOutputDirectory Value="False"/>
<CompatibilityMode Value="True"/>
</Flags>
<SessionStorage Value="InIDEConfig"/>
<MainUnit Value="0"/>
<Title Value="Lazarus"/>
<Scaled Value="True"/>
<ResourceType Value="res"/>
@ -36,7 +36,6 @@
</PublishOptions>
<RunParams>
<FormatVersion Value="2"/>
<Modes Count="0"/>
</RunParams>
<RequiredPackages Count="7">
<Item1>
@ -62,7 +61,7 @@
<PackageName Value="SynEdit"/>
</Item7>
</RequiredPackages>
<Units Count="243">
<Units Count="242">
<Unit0>
<Filename Value="lazarus.pp"/>
<IsPartOfProject Value="True"/>
@ -1306,7 +1305,10 @@
<Unit220>
<Filename Value="allcompileroptions.pas"/>
<IsPartOfProject Value="True"/>
<ComponentName Value="frmAllCompilerOptions"/>
<HasResources Value="True"/>
<ResourceBaseClass Value="Form"/>
<UnitName Value="AllCompilerOptions"/>
</Unit220>
<Unit221>
<Filename Value="jumphistoryview.pas"/>
@ -1351,79 +1353,75 @@
<IsPartOfProject Value="True"/>
</Unit229>
<Unit230>
<Filename Value="objectlists.pas"/>
<IsPartOfProject Value="True"/>
</Unit230>
<Unit231>
<Filename Value="mouseactiondialog.pas"/>
<IsPartOfProject Value="True"/>
<HasResources Value="True"/>
</Unit231>
<Unit232>
</Unit230>
<Unit231>
<Filename Value="basedebugmanager.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="BaseDebugManager"/>
</Unit232>
<Unit233>
</Unit231>
<Unit232>
<Filename Value="imexportcompileropts.pas"/>
<IsPartOfProject Value="True"/>
<ComponentName Value="ImExportCompOptsDlg"/>
<HasResources Value="True"/>
<ResourceBaseClass Value="Form"/>
</Unit233>
<Unit234>
</Unit232>
<Unit233>
<Filename Value="initialsetupproc.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="InitialSetupProc"/>
</Unit234>
<Unit235>
</Unit233>
<Unit234>
<Filename Value="qfinitlocalvardlg.pas"/>
<IsPartOfProject Value="True"/>
<ComponentName Value="QFInitLocalVarDialog"/>
<HasResources Value="True"/>
<ResourceBaseClass Value="Form"/>
</Unit235>
<Unit236>
</Unit234>
<Unit235>
<Filename Value="../packager/interpkgconflictfiles.pas"/>
<IsPartOfProject Value="True"/>
<HasResources Value="True"/>
</Unit236>
<Unit237>
</Unit235>
<Unit236>
<Filename Value="encloseifdef.pas"/>
<IsPartOfProject Value="True"/>
<ComponentName Value="EncloseIfDefForm"/>
<HasResources Value="True"/>
<ResourceBaseClass Value="Form"/>
<UnitName Value="EncloseIfDef"/>
</Unit237>
<Unit238>
</Unit236>
<Unit237>
<Filename Value="definesgui.pas"/>
<IsPartOfProject Value="True"/>
<ComponentName Value="DefinesGuiForm"/>
<HasResources Value="True"/>
<ResourceBaseClass Value="Form"/>
<UnitName Value="DefinesGui"/>
</Unit238>
<Unit239>
</Unit237>
<Unit238>
<Filename Value="inputhistorywithsearchopt.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="InputhistoryWithSearchOpt"/>
</Unit239>
<Unit240>
</Unit238>
<Unit239>
<Filename Value="projectdescriptors.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="ProjectDescriptors"/>
</Unit240>
<Unit241>
</Unit239>
<Unit240>
<Filename Value="etpas2jsmsgparser.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="etPas2jsMsgParser"/>
</Unit241>
<Unit242>
</Unit240>
<Unit241>
<Filename Value="exttoolside.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="ExtToolsIDE"/>
</Unit242>
</Unit241>
</Units>
</ProjectOptions>
<CompilerOptions>

View File

@ -52,7 +52,7 @@ uses
Forms, Controls, Dialogs, Menus, ComCtrls, LResources,
// LazUtils
LazUTF8, Laz2_XMLCfg, LazUTF8Classes, LazTracer, LazUtilities, LazStringUtils,
LazFileUtils, LazFileCache, StringHashList, Translations, AvgLvlTree,
LazFileUtils, LazFileCache, StringHashList, AvgLvlTree, ObjectLists, Translations,
// Codetools
CodeToolsConfig, CodeToolManager, CodeCache, BasicCodeTools,
FileProcs, CodeTree, CTUnitGraph,
@ -62,10 +62,9 @@ uses
IDEExternToolIntf, MacroIntf, LazIDEIntf, IDEMsgIntf, SrcEditorIntf,
ComponentReg, ComponentEditors, PropEdits, IDEDialogs, UnitResources,
// IDE
IDECmdLine, LazarusIDEStrConsts, IDEProcs, ObjectLists,
DialogProcs, IDEOptionDefs, EnvironmentOpts,
MiscOptions, InputHistory, Project, PackageEditor, AddToPackageDlg,
PackageDefs, PackageLinks, PackageSystem, OpenInstalledPkgDlg,
IDECmdLine, LazarusIDEStrConsts, IDEProcs, DialogProcs, IDEOptionDefs,
EnvironmentOpts, MiscOptions, InputHistory, Project, PackageEditor,
AddToPackageDlg, PackageDefs, PackageLinks, PackageSystem, OpenInstalledPkgDlg,
PkgGraphExplorer, BrokenDependenciesDlg, CompilerOptions, IDETranslations,
TransferMacros, BuildLazDialog, NewDialog, FindInFilesDlg, ProjectInspector,
SourceEditor, ProjPackChecks, AddFileToAPackageDlg, LazarusPackageIntf,
@ -74,6 +73,10 @@ uses
MainBar, MainIntf, MainBase, ModeMatrixOpts;
type
TPackagePackageArray = specialize TObjectArray<TLazPackageID, TLazPackageID>;
TOwnerPackageArray = specialize TObjectArray<TObject, TLazPackageID>;
{ TPkgManager }
TPkgManager = class(TBasePkgManager)
@ -361,13 +364,13 @@ type
ComponentClassnames: TStrings;
Quiet: boolean = false): TModalResult; override;
function GetUnitsAndDependenciesForComponents(ComponentClassNames: TStrings;
out PackageList: TObjectArray; out UnitList: TStrings): TModalResult;
out PackageList: TPackagePackageArray; out UnitList: TStringList): TModalResult;
function GetMissingDependenciesForUnit(const UnitFilename: string;
ComponentClassnames: TStrings;
var List: TObjectArray): TModalResult;
var List: TOwnerPackageArray): TModalResult;
function FilterMissingDependenciesForUnit(const UnitFilename: string;
InputPackageList: TObjectArray;
out OutputPackageList: TObjectArray): TModalResult;
InputPackageList: TPackagePackageArray;
out OutputPackageList: TOwnerPackageArray): TModalResult;
function GetUsableComponentUnits(CurRoot: TPersistent): TFPList; override; // list of TUnitInfo
procedure IterateComponentNames(CurRoot: TPersistent; TypeData: PTypeData;
Proc: TGetStrProc); override;
@ -4307,10 +4310,8 @@ var
i: Integer;
begin
Result:='';
if FilenameIsAbsolute(Filename) then begin
Result:=Filename;
exit;
end;
if FilenameIsAbsolute(Filename) then
exit(Filename);
PkgList:=nil;
PackageGraph.GetAllRequiredPackages(nil,aProject.FirstRequiredDependency,
PkgList,[pirCompileOrder]);
@ -4319,8 +4320,7 @@ begin
for i:=0 to PkgList.Count-1 do begin
APackage:=TLazPackage(PkgList[i]);
IncPath:=APackage.CompilerOptions.GetIncludePath(false);
Result:=SearchFileInPath(Filename,APackage.Directory,IncPath,';',
ctsfcDefault);
Result:=SearchFileInPath(Filename,APackage.Directory,IncPath,';',ctsfcDefault);
if Result<>'' then exit;
end;
finally
@ -4355,9 +4355,9 @@ function TPkgManager.AddUnitDependenciesForComponentClasses(
Quiet: boolean): TModalResult;
var
UnitBuf: TCodeBuffer;
UnitNames: TStrings;
Dependencies, MissingDependencies: TObjectArray;
UnitNames: TStringList;
MissingDependencies: TOwnerPackageArray;
function LoadAndParseUnitBuf: TModalResult;
begin
if not CodeToolBoss.GatherExternalChanges then begin
@ -4422,8 +4422,8 @@ var
PackageAdditions:='';
if MissingDependencies<>nil then begin
for i:=0 to MissingDependencies.Count-1 do begin
UnitOwner:=TObject(MissingDependencies[i]);
RequiredPackage:=TLazPackageID(MissingDependencies.Objects[i]);
UnitOwner:=MissingDependencies[i];
RequiredPackage:=MissingDependencies.Objects[i];
if RequiredPackage is TIDEPackage then
RequiredPackage:=RedirectPackageDependency(TIDEPackage(RequiredPackage));
if UnitOwner is TProject then begin
@ -4460,8 +4460,8 @@ var
begin
if MissingDependencies<>nil then begin
for i:=0 to MissingDependencies.Count-1 do begin
UnitOwner:=TObject(MissingDependencies[i]);
RequiredPackage:=TLazPackageID(MissingDependencies.Objects[i]);
UnitOwner:=MissingDependencies[i];
RequiredPackage:=MissingDependencies.Objects[i];
if RequiredPackage is TIDEPackage then
RequiredPackage:=RedirectPackageDependency(TIDEPackage(RequiredPackage));
if UnitOwner is TProject then begin
@ -4496,6 +4496,9 @@ var
Result:=mrOk;
end;
var
Dependencies: TPackagePackageArray;
begin
Result:=mrCancel;
UnitNames:=nil;
@ -4535,8 +4538,8 @@ begin
end;
function TPkgManager.GetUnitsAndDependenciesForComponents(
ComponentClassNames: TStrings; out PackageList: TObjectArray;
out UnitList: TStrings): TModalResult;
ComponentClassNames: TStrings; out PackageList: TPackagePackageArray;
out UnitList: TStringList): TModalResult;
// returns a list of packages and units needed to use the Component in the unit
var
CurClassID: Integer;
@ -4546,7 +4549,8 @@ var
PkgFile: TPkgFile;
RequiredPackage: TLazPackageID;
CurUnitName: String;
CurPackages, AllPackages, CurUnitNames: TStrings;
CurUnitNames: TStrings;
CurPackages, AllPackages: TStringList;
CurCompReq: TComponentRequirements;
Helper: TPackageIterateHelper;
begin
@ -4578,8 +4582,8 @@ begin
for CurUnitIdx:=0 to CurUnitNames.Count-1 do begin
if UnitList=nil then begin
UnitList:=TStringList.Create;
TStringList(UnitList).CaseSensitive:=False;
TStringList(UnitList).Duplicates:=dupIgnore;
UnitList.CaseSensitive:=False;
UnitList.Duplicates:=dupIgnore;
end;
CurUnitName:=CurUnitNames[CurUnitIdx];
UnitList.Add(CurUnitName);
@ -4593,8 +4597,8 @@ begin
if RequiredPackage<>nil then begin
if CurPackages=nil then begin
CurPackages:=TStringList.Create;
TStringList(CurPackages).Duplicates:=dupIgnore;
TStringList(CurPackages).CaseSensitive:=False;
CurPackages.Duplicates:=dupIgnore;
CurPackages.CaseSensitive:=False;
end else
CurPackages.Clear;
CurPackages.Add(RequiredPackage.Name);
@ -4604,8 +4608,8 @@ begin
try
if AllPackages=nil then begin
AllPackages:=TStringList.Create;
TStringList(AllPackages).CaseSensitive:=False;
TStringList(AllPackages).Duplicates:=dupIgnore;
AllPackages.CaseSensitive:=False;
AllPackages.Duplicates:=dupIgnore;
end;
Helper.PackageNames:=CurPackages;
Helper.PackageList:=AllPackages;
@ -4623,9 +4627,10 @@ begin
end;
end;
if AllPackages.Count>0 then begin
if AllPackages.Count>0 then PackageList:=TObjectArray.Create;
if AllPackages.Count>0 then
PackageList:=TPackagePackageArray.Create;
for CurPackageIdx:=0 to AllPackages.Count-1 do
PackageList.Add(AllPackages.Objects[CurPackageIdx]);
PackageList.Add(TLazPackageID(AllPackages.Objects[CurPackageIdx]));
end;
finally
CurUnitNames.Free;
@ -4636,8 +4641,8 @@ begin
end;
function TPkgManager.FilterMissingDependenciesForUnit(const UnitFilename: string;
InputPackageList: TObjectArray;
out OutputPackageList: TObjectArray): TModalResult;
InputPackageList: TPackagePackageArray;
out OutputPackageList: TOwnerPackageArray): TModalResult;
// returns a list of packages that are not yet used by the project the unit
// belongs to
var
@ -4660,15 +4665,14 @@ begin
else
FirstDependency:=nil;
for CurPackageIdx:=0 to InputPackageList.Count-1 do begin
RequiredPackage:=TLazPackageID(InputPackageList.Items[CurPackageIdx]);
RequiredPackage:=InputPackageList.Items[CurPackageIdx];
if (RequiredPackage<>nil)
and (RequiredPackage<>UnitOwner)
and (FindCompatibleDependencyInList(FirstDependency,pdlRequires,
RequiredPackage)=nil)
and (PackageGraph.FindPackageProvidingName(FirstDependency,
RequiredPackage.Name)=nil)
and (FindCompatibleDependencyInList(FirstDependency,pdlRequires,RequiredPackage)=nil)
and (PackageGraph.FindPackageProvidingName(FirstDependency,RequiredPackage.Name)=nil)
then begin
if OutputPackageList=nil then OutputPackageList:=TObjectArray.Create;
if OutputPackageList=nil then
OutputPackageList:=TOwnerPackageArray.Create;
OutputPackageList.AddObject(UnitOwner,RequiredPackage);
//debugln(['TPkgManager.FilterMissingDependenciesForUnit A ',UnitOwner.ClassName,' ',RequiredPackage.Name]);
//if TObject(OutputPackageList[OutputPackageList.Count-1])<>UnitOwner then RaiseGDBException('A');
@ -4685,17 +4689,16 @@ end;
function TPkgManager.GetMissingDependenciesForUnit(
const UnitFilename: string; ComponentClassnames: TStrings;
var List: TObjectArray): TModalResult;
var List: TOwnerPackageArray): TModalResult;
// returns a list of packages needed to use the Component in the unit
var
AllPackages: TObjectArray;
AllUnits: TStrings;
AllPackages: TPackagePackageArray;
AllUnits: TStringList;
begin
List:=nil;
Result:=GetUnitsAndDependenciesForComponents(ComponentClassnames,AllPackages,AllUnits);
try
if Result<>mrOK then Exit;
Result:=FilterMissingDependenciesForUnit(UnitFilename,AllPackages,List);
finally
AllPackages.Free;