|
@@ -10786,6 +10786,24 @@ begin
|
|
[GetElementTypeName(FoundEl)+' '+FoundEl.Name],NameExpr);
|
|
[GetElementTypeName(FoundEl)+' '+FoundEl.Name],NameExpr);
|
|
end;
|
|
end;
|
|
|
|
|
|
|
|
+ if FoundEl is TPasType then
|
|
|
|
+ begin
|
|
|
|
+ // typecast
|
|
|
|
+ TypeEl:=ResolveAliasType(TPasType(FoundEl));
|
|
|
|
+ C:=TypeEl.ClassType;
|
|
|
|
+ if C=TPasUnresolvedSymbolRef then
|
|
|
|
+ begin
|
|
|
|
+ // typecast to built-in type
|
|
|
|
+ if TypeEl.CustomData is TResElDataBaseType then
|
|
|
|
+ CheckTypeCast(TypeEl,Params,true); // emit warnings
|
|
|
|
+ end
|
|
|
|
+ else
|
|
|
|
+ begin
|
|
|
|
+ // typecast to user type
|
|
|
|
+ CheckTypeCast(TypeEl,Params,true); // emit warnings
|
|
|
|
+ end;
|
|
|
|
+ end;
|
|
|
|
+
|
|
// FoundEl compatible element -> create reference
|
|
// FoundEl compatible element -> create reference
|
|
Ref:=CreateReference(FoundEl,NameExpr,rraRead);
|
|
Ref:=CreateReference(FoundEl,NameExpr,rraRead);
|
|
if FindCallData.StartScope.ClassType=ScopeClass_WithExpr then
|
|
if FindCallData.StartScope.ClassType=ScopeClass_WithExpr then
|
|
@@ -26101,8 +26119,18 @@ end;
|
|
function TPasResolver.CheckTypeCastRes(const FromResolved,
|
|
function TPasResolver.CheckTypeCastRes(const FromResolved,
|
|
ToResolved: TPasResolverResult; ErrorEl: TPasElement; RaiseOnError: boolean
|
|
ToResolved: TPasResolverResult; ErrorEl: TPasElement; RaiseOnError: boolean
|
|
): integer;
|
|
): integer;
|
|
|
|
+
|
|
|
|
+ procedure WarnClassTypesAreNotRelated(GotType, ExpType: TPasClassType);
|
|
|
|
+ var
|
|
|
|
+ GotDesc, ExpDesc: String;
|
|
|
|
+ begin
|
|
|
|
+ GetIncompatibleTypeDesc(GotType,ExpType,GotDesc,ExpDesc);
|
|
|
|
+ LogMsg(20200209140450,mtWarning,nClassTypesAreNotRelatedXY,
|
|
|
|
+ sClassTypesAreNotRelatedXY,[GotDesc,ExpDesc],ErrorEl);
|
|
|
|
+ end;
|
|
|
|
+
|
|
var
|
|
var
|
|
- ToTypeEl, ToClassType, FromClassType, FromTypeEl: TPasType;
|
|
|
|
|
|
+ ToTypeEl, ToType, FromType, FromTypeEl: TPasType;
|
|
ToTypeBaseType: TResolverBaseType;
|
|
ToTypeBaseType: TResolverBaseType;
|
|
C: TClass;
|
|
C: TClass;
|
|
ToProcType, FromProcType: TPasProcedureType;
|
|
ToProcType, FromProcType: TPasProcedureType;
|
|
@@ -26110,6 +26138,7 @@ var
|
|
i: Integer;
|
|
i: Integer;
|
|
ConToken: TToken;
|
|
ConToken: TToken;
|
|
ConEl: TPasElement;
|
|
ConEl: TPasElement;
|
|
|
|
+ ToClassType, FromClassType: TPasClassType;
|
|
begin
|
|
begin
|
|
Result:=cIncompatible;
|
|
Result:=cIncompatible;
|
|
ToTypeEl:=ToResolved.LoTypeEl;
|
|
ToTypeEl:=ToResolved.LoTypeEl;
|
|
@@ -26229,34 +26258,39 @@ begin
|
|
end
|
|
end
|
|
else if C=TPasClassType then
|
|
else if C=TPasClassType then
|
|
begin
|
|
begin
|
|
|
|
+ ToClassType:=TPasClassType(ToTypeEl);
|
|
// to class
|
|
// to class
|
|
if FromResolved.BaseType=btContext then
|
|
if FromResolved.BaseType=btContext then
|
|
begin
|
|
begin
|
|
FromTypeEl:=FromResolved.LoTypeEl;
|
|
FromTypeEl:=FromResolved.LoTypeEl;
|
|
if FromTypeEl.ClassType=TPasClassType then
|
|
if FromTypeEl.ClassType=TPasClassType then
|
|
begin
|
|
begin
|
|
|
|
+ FromClassType:=TPasClassType(FromTypeEl);
|
|
if FromResolved.IdentEl is TPasType then
|
|
if FromResolved.IdentEl is TPasType then
|
|
RaiseMsg(20170404162606,nCannotTypecastAType,sCannotTypecastAType,[],ErrorEl);
|
|
RaiseMsg(20170404162606,nCannotTypecastAType,sCannotTypecastAType,[],ErrorEl);
|
|
- if TPasClassType(FromTypeEl).ObjKind=TPasClassType(ToTypeEl).ObjKind then
|
|
|
|
|
|
+ if FromClassType.ObjKind=ToClassType.ObjKind then
|
|
begin
|
|
begin
|
|
// type cast upwards or downwards
|
|
// type cast upwards or downwards
|
|
Result:=CheckSrcIsADstType(FromResolved,ToResolved);
|
|
Result:=CheckSrcIsADstType(FromResolved,ToResolved);
|
|
if Result=cIncompatible then
|
|
if Result=cIncompatible then
|
|
Result:=CheckSrcIsADstType(ToResolved,FromResolved);
|
|
Result:=CheckSrcIsADstType(ToResolved,FromResolved);
|
|
|
|
+ if RaiseOnError then
|
|
|
|
+ WarnClassTypesAreNotRelated(FromClassType,ToClassType);
|
|
|
|
+ Result:=cCompatible;
|
|
end
|
|
end
|
|
- else if TPasClassType(ToTypeEl).ObjKind=okInterface then
|
|
|
|
|
|
+ else if ToClassType.ObjKind=okInterface then
|
|
begin
|
|
begin
|
|
- if (TPasClassType(FromTypeEl).ObjKind=okClass)
|
|
|
|
- and (not TPasClassType(FromTypeEl).IsExternal) then
|
|
|
|
|
|
+ if (FromClassType.ObjKind=okClass)
|
|
|
|
+ and (not FromClassType.IsExternal) then
|
|
begin
|
|
begin
|
|
// e.g. intftype(classinstvar)
|
|
// e.g. intftype(classinstvar)
|
|
Result:=cCompatible;
|
|
Result:=cCompatible;
|
|
end;
|
|
end;
|
|
end
|
|
end
|
|
- else if TPasClassType(FromTypeEl).ObjKind=okInterface then
|
|
|
|
|
|
+ else if FromClassType.ObjKind=okInterface then
|
|
begin
|
|
begin
|
|
- if (TPasClassType(ToTypeEl).ObjKind=okClass)
|
|
|
|
- and (not TPasClassType(ToTypeEl).IsExternal) then
|
|
|
|
|
|
+ if (ToClassType.ObjKind=okClass)
|
|
|
|
+ and (not ToClassType.IsExternal) then
|
|
begin
|
|
begin
|
|
// e.g. classtype(intfvar)
|
|
// e.g. classtype(intfvar)
|
|
Result:=cCompatible;
|
|
Result:=cCompatible;
|
|
@@ -26339,9 +26373,9 @@ begin
|
|
if (FromResolved.IdentEl is TPasType) then
|
|
if (FromResolved.IdentEl is TPasType) then
|
|
RaiseMsg(20170404162604,nCannotTypecastAType,sCannotTypecastAType,[],ErrorEl);
|
|
RaiseMsg(20170404162604,nCannotTypecastAType,sCannotTypecastAType,[],ErrorEl);
|
|
// type cast classof(classof-var) upwards or downwards
|
|
// type cast classof(classof-var) upwards or downwards
|
|
- ToClassType:=TPasClassOfType(ToTypeEl).DestType;
|
|
|
|
- FromClassType:=TPasClassOfType(FromResolved.LoTypeEl).DestType;
|
|
|
|
- Result:=CheckClassesAreRelated(ToClassType,FromClassType);
|
|
|
|
|
|
+ ToType:=TPasClassOfType(ToTypeEl).DestType;
|
|
|
|
+ FromType:=TPasClassOfType(FromResolved.LoTypeEl).DestType;
|
|
|
|
+ Result:=CheckClassesAreRelated(ToType,FromType);
|
|
end;
|
|
end;
|
|
end
|
|
end
|
|
else if FromResolved.BaseType=btPointer then
|
|
else if FromResolved.BaseType=btPointer then
|
|
@@ -26526,9 +26560,9 @@ begin
|
|
and (ToTypeEl=ToResolved.IdentEl) then
|
|
and (ToTypeEl=ToResolved.IdentEl) then
|
|
begin
|
|
begin
|
|
// for example class-of(Self) in a class function
|
|
// for example class-of(Self) in a class function
|
|
- ToClassType:=TPasClassOfType(ToTypeEl).DestType;
|
|
|
|
- FromClassType:=TPasClassType(FromTypeEl);
|
|
|
|
- Result:=CheckClassesAreRelated(ToClassType,FromClassType);
|
|
|
|
|
|
+ ToType:=TPasClassOfType(ToTypeEl).DestType;
|
|
|
|
+ FromType:=TPasClassType(FromTypeEl);
|
|
|
|
+ Result:=CheckClassesAreRelated(ToType,FromType);
|
|
end;
|
|
end;
|
|
end;
|
|
end;
|
|
end;
|
|
end;
|