pastojs: filer: generic class

git-svn-id: trunk@43960 -
This commit is contained in:
Mattias Gaertner 2020-01-16 21:23:15 +00:00
parent 887c5e81b2
commit 2d9975fdcc
4 changed files with 39 additions and 13 deletions

View File

@ -27915,7 +27915,8 @@ begin
Templates:=GetProcTemplateTypes(Proc); Templates:=GetProcTemplateTypes(Proc);
if (Templates<>nil) and (Templates.Count>0) then if (Templates<>nil) and (Templates.Count>0) then
exit(false); exit(false);
if ProcScope.SpecializedFromItem=nil then exit(true); if ProcScope.SpecializedFromItem=nil then
exit(true);
Params:=ProcScope.SpecializedFromItem.Params; Params:=ProcScope.SpecializedFromItem.Params;
for i:=0 to length(Params)-1 do for i:=0 to length(Params)-1 do
if Params[i] is TPasGenericTemplateType then exit(false); if Params[i] is TPasGenericTemplateType then exit(false);

View File

@ -1079,6 +1079,7 @@ function TPasAnalyzer.CanSkipGenericProc(DeclProc: TPasProcedure): boolean;
var var
Templates: TFPList; Templates: TFPList;
Parent: TPasElement;
begin begin
Result:=false; Result:=false;
if ScopeModule=nil then if ScopeModule=nil then
@ -1093,14 +1094,29 @@ begin
Templates:=Resolver.GetProcTemplateTypes(DeclProc); Templates:=Resolver.GetProcTemplateTypes(DeclProc);
if (Templates<>nil) and (Templates.Count>0) then if (Templates<>nil) and (Templates.Count>0) then
begin begin
// generic template // generic procedure
if paoSkipGenericProc in Options then if paoSkipGenericProc in Options then
exit(true); // exit(true); // emit no hints for generic proc
// -> analyze // -> analyze
end end
else if not Resolver.IsFullySpecialized(DeclProc) then else if not Resolver.IsFullySpecialized(DeclProc) then
// half specialized -> skip // half specialized -> skip
exit(true); exit(true)
else if paoSkipGenericProc in Options then
begin
Parent:=DeclProc.Parent;
while Parent<>nil do
begin
if (Parent is TPasGenericType) then
begin
Templates:=TPasGenericType(Parent).GenericTemplateTypes;
if (Templates<>nil) and (Templates.Count>0) then
// procedure of a generic parent -> emit no hints
exit(true);
end;
Parent:=Parent.Parent;
end;
end;
end; end;
end; end;

View File

@ -3721,7 +3721,7 @@ begin
Templ:=TPasGenericTemplateType(GenericTemplateTypes[i]); Templ:=TPasGenericTemplateType(GenericTemplateTypes[i]);
TemplObj:=TJSONObject.Create; TemplObj:=TJSONObject.Create;
Arr.Add(TemplObj); Arr.Add(TemplObj);
TemplObj.Add('Name',Templ.Name); WritePasElement(TemplObj,Templ,aContext);
WriteElementArray(TemplObj,Parent,'Constraints',Templ.Constraints,aContext,true); WriteElementArray(TemplObj,Parent,'Constraints',Templ.Constraints,aContext,true);
end; end;
end; end;
@ -6300,7 +6300,7 @@ var
begin begin
if not ReadArray(Obj,'Declarations',Arr,Decls) then exit; if not ReadArray(Obj,'Declarations',Arr,Decls) then exit;
{$IFDEF VerbosePCUFiler} {$IFDEF VerbosePCUFiler}
writeln('TPCUReader.ReadDeclarations ',GetObjName(Section),' ',Arr.Count); writeln('TPCUReader.ReadDeclarations ',GetObjName(Decls),' ',Arr.Count);
{$ENDIF} {$ENDIF}
for i:=0 to Arr.Count-1 do for i:=0 to Arr.Count-1 do
begin begin
@ -7551,6 +7551,7 @@ begin
RaiseMsg(20190720224130,Parent,IntToStr(i)); RaiseMsg(20190720224130,Parent,IntToStr(i));
GenType:=TPasGenericTemplateType(CreateElement(TPasGenericTemplateType,GenTypeName,Parent)); GenType:=TPasGenericTemplateType(CreateElement(TPasGenericTemplateType,GenTypeName,Parent));
GenericTemplateTypes.Add(GenType); GenericTemplateTypes.Add(GenType);
ReadPasElement(TemplObj,GenType,aContext);
ReadElementArray(TemplObj,Parent,'Constraints',GenType.Constraints, ReadElementArray(TemplObj,Parent,'Constraints',GenType.Constraints,
{$IFDEF CheckPasTreeRefCount}'TPasGenericTemplateType.Constraints'{$ELSE}true{$ENDIF}, {$IFDEF CheckPasTreeRefCount}'TPasGenericTemplateType.Constraints'{$ELSE}true{$ENDIF},
aContext); aContext);

View File

@ -1171,10 +1171,20 @@ begin
//writeln('TCustomTestPrecompile.CheckRestoredElement Checking Parent... Orig=',GetObjName(Orig),' Rest=',GetObjName(Rest)); //writeln('TCustomTestPrecompile.CheckRestoredElement Checking Parent... Orig=',GetObjName(Orig),' Rest=',GetObjName(Rest));
CheckRestoredReference(Path+'.Parent',Orig.Parent,Rest.Parent); CheckRestoredReference(Path+'.Parent',Orig.Parent,Rest.Parent);
//writeln('TCustomTestPrecompile.CheckRestoredElement Checking CustomData... Orig=',GetObjName(Orig),' Rest=',GetObjName(Rest));
CheckRestoredCustomData(Path+'.CustomData',Rest,Orig.CustomData,Rest.CustomData,Flags);
C:=Orig.ClassType; C:=Orig.ClassType;
//writeln('TCustomTestPrecompile.CheckRestoredElement Checking CustomData... Orig=',GetObjName(Orig),' Rest=',GetObjName(Rest));
if C=TPasGenericTemplateType then
begin
// TPasGenericParamsScope is only needed during parsing
if Orig.CustomData=nil then
else if not (Orig.CustomData is TPasGenericParamsScope) then
Fail(Path+'Orig.CustomData='+GetObjName(Orig.CustomData))
else if Rest.CustomData<>nil then
CheckRestoredCustomData(Path+'.CustomData',Rest,Orig.CustomData,Rest.CustomData,Flags);
end
else
CheckRestoredCustomData(Path+'.CustomData',Rest,Orig.CustomData,Rest.CustomData,Flags);
if C=TUnaryExpr then if C=TUnaryExpr then
CheckRestoredUnaryExpr(Path,TUnaryExpr(Orig),TUnaryExpr(Rest),Flags) CheckRestoredUnaryExpr(Path,TUnaryExpr(Orig),TUnaryExpr(Rest),Flags)
else if C=TBinaryExpr then else if C=TBinaryExpr then
@ -2671,8 +2681,6 @@ end;
procedure TTestPrecompile.TestPC_GenericClass; procedure TTestPrecompile.TestPC_GenericClass;
begin begin
exit;
StartUnit(false); StartUnit(false);
Add([ Add([
'interface', 'interface',
@ -2681,10 +2689,10 @@ begin
' end;', ' end;',
' generic TBird<T> = class', ' generic TBird<T> = class',
' a: T;', ' a: T;',
' generic function Run<T>(a: T): T;', ' function Run: T;',
' end;', ' end;',
'implementation', 'implementation',
'function TBird.Run<T>(a: T): T;', 'function TBird.Run: T;',
'var b: T;', 'var b: T;',
'begin', 'begin',
' b:=a; Result:=b;', ' b:=a; Result:=b;',