passrc: improve parsing code statements. TPasImplCommand replaced by actual simple or assignment. Small fix for the expression parser to handle dot separated identifier

git-svn-id: trunk@15909 -
This commit is contained in:
dmitry 2010-08-26 08:10:54 +00:00
parent 621f28cd1d
commit c3095bf873
2 changed files with 64 additions and 34 deletions

View File

@ -759,6 +759,8 @@ type
TPasImplTry = class;
TPasImplExceptOn = class;
TPasImplRaise = class;
TPasImplAssign = class;
TPasImplSimple = class;
TPasImplLabelMark = class;
{ TPasImplBlock }
@ -784,6 +786,8 @@ type
function AddExceptOn(const VarName, TypeName: string): TPasImplExceptOn;
function AddRaise: TPasImplRaise;
function AddLabelMark(const Id: string): TPasImplLabelMark;
function AddAssign(left, right: TPasExpr): TPasImplAssign;
function AddSimple(exp: TPasExpr): TPasImplSimple;
function CloseOnSemicolon: boolean; virtual;
public
Elements: TList; // TPasImplElement objects
@ -902,6 +906,21 @@ type
Body: TPasImplElement;
end;
{ TPasImplAssign }
TPasImplAssign = class (TPasImplStatement)
public
left : TPasExpr;
right : TPasExpr;
end;
{ TPasImplSimple }
TPasImplSimple = class (TPasImplStatement)
public
expr : TPasExpr;
end;
TPasImplTryHandler = class;
TPasImplTryFinally = class;
TPasImplTryExcept = class;
@ -1690,11 +1709,24 @@ end;
function TPasImplBlock.AddLabelMark(const Id: string): TPasImplLabelMark;
begin
Result:=TPasIMplLabelMark.Create('', Self);
Result:=TPasImplLabelMark.Create('', Self);
Result.LabelId:=Id;
AddElement(Result);
end;
function TPasImplBlock.AddAssign(left,right:TPasExpr):TPasImplAssign;
begin
Result:=TPasImplAssign.Create('', Self);
Result.left:=left;
Result.right:=right;
end;
function TPasImplBlock.AddSimple(exp:TPasExpr):TPasImplSimple;
begin
Result:=TPasImplSimple.Create('', Self);
Result.expr:=exp;
end;
function TPasImplBlock.CloseOnSemicolon: boolean;
begin
Result:=false;

View File

@ -933,6 +933,13 @@ begin
x:=DoParseExpression(AParent);
if CurToken<>tkBraceClose then Exit;
NextToken;
// for the expression like (TObject(m)).Free;
if CurToken = tkDot then begin
NextToken;
x:=TBinaryExpr.Create(AParent,x, ParseExpIdent(AParent), TokenToExprOp(tkDot));
end;
end else begin
x:=ParseExpIdent(AParent);
end;
@ -2669,15 +2676,16 @@ var
var
Condition: String;
Command: String;
StartValue: String;
VarName: String;
EndValue: String;
Expr: String;
SubBlock: TPasImplElement;
CmdElem: TPasImplCommand;
CmdElem: TPasImplElement;
TypeName: String;
ForDownTo: Boolean;
left: TPasExpr;
right: TPasExpr;
begin
NewImplElement:=nil;
CurBlock := Parent;
@ -2911,42 +2919,32 @@ begin
ParseExc(SParserSyntaxError);
end;
else
UngetToken;
Command:='';
NextToken;
// testing for label mark
if CurToken=tkIdentifier then
begin
Command:=CurTokenText;
NextToken;
// testing for the goto mark
if CurToken=tkColon then
left:=DoParseExpression(nil);
case CurToken of
tkAssign:
begin
CurBlock.AddLabelMark(Command);
end
else
begin
Command:='';
UngetToken;
// assign statement
NextToken;
right:=ParseExpIdent(Parent);
CmdElem:=CurBlock.AddAssign(left, right);
UngetToken;
end;
end else
tkColon:
begin
if not (left is TPrimitiveExpr) then
ParseExc(Format(SParserExpectTokenError, [TokenInfos[tkSemicolon]]));
// label mark. todo: check mark identifier in the list of labels
CmdElem:=CurBlock.AddLabelMark(TPrimitiveExpr(left).Value);
left.Free;
end
else
// simple statement (function call)
CmdElem:=CurBlock.AddSimple(left);
UngetToken;
if Command='' then
begin
// parsing the assignment statement or call expression
Command:=ParseCommand;
//WriteLn(i,'COMMAND="',Command,'" Token=',CurTokenString);
if Command='' then
ParseExc(SParserSyntaxError);
CmdElem:=CurBlock.AddCommand(Command);
if NewImplElement=nil then NewImplElement:=CmdElem;
if CloseStatement(false) then break;
end;
if not (CmdElem is TPasImplLabelMark) then
if NewImplElement=nil then NewImplElement:=CmdElem;
end;
end;
end;