Recent

Author Topic: It has a little bug in IDE  (Read 10690 times)

fpccn_ljz

  • Newbie
  • Posts: 1
It has a little bug in IDE
« on: June 19, 2021, 03:47:00 am »
I had found a little bug in IDE :

if the last column lost ' ; ' ,IED can't find .

speter

  • Full Member
  • ***
  • Posts: 217
Re: It has a little bug in IDE
« Reply #1 on: June 19, 2021, 03:54:27 am »
That is not a bug.

Pascal has allowed that syntax since the 1980's.

cheers
S.
I climbed mighty mountains, and saw that they were actually tiny foothills. :)

Laz 2.0.10 / FPC 3.2.0 / Windows 10 (64bit)

lucamar

  • Hero Member
  • *****
  • Posts: 4165
Re: It has a little bug in IDE
« Reply #2 on: June 19, 2021, 05:32:25 am »
In fact, that extra ";" we all put there is really a new empty sentence ;)

And we might thank the gods it's "allowed", otherwise the little "else" problem* most of us have seen sometime or other would reach monster proportions :D


* I mean the "problem" that there can't be a ";" before he else in an if...else ... which while no problem at all, can catch you unaware sometimes.
Turbo Pascal 3 CP/M - Amstrad PCW 8256 (512 KB !!!) :P
Lazarus/FPC 2.0.8/3.0.4 & 2.0.12/3.2.0 - 32/64 bits on:
(K|L|X)Ubuntu 12..18, Windows XP, 7, 10 and various DOSes.

440bx

  • Hero Member
  • *****
  • Posts: 2443
Re: It has a little bug in IDE
« Reply #3 on: June 19, 2021, 07:36:33 am »
I had found a little bug in IDE :

if the last column lost ' ; ' ,IED can't find .
The semicolon in Pascal is a statement separator and "end" is not a statement, therefore in strict Pascal, a semicolon should not precede the "end" keyword.

Many implementations of Pascal, including FPC and Delphi allow "extra" semicolons because treating the ";" strictly as a separator (which is what it is in Pascal) proved confusing for many programmers.

Just for fun, declare a record (anything you want, doesn't matter) and don't put a semicolon at the end of the last field (which should be followed by the record terminator "end" keyword) and you'll notice that the semicolon isn't required there either.
FPC v3.0.4 and Lazarus 1.8.2 on Windows 7 64bit.

lucamar

  • Hero Member
  • *****
  • Posts: 4165
Re: It has a little bug in IDE
« Reply #4 on: June 19, 2021, 08:03:23 am »
The semicolon in Pascal is a statement separator and "end" is not a statement, therefore in strict Pascal, a semicolon should not precede the "end" keyword.

As demonstrated by the fact that it's not allowed before an "else" even after an "end", as in:
Code: Pascal  [Select][+][-]
  1. if ... then
  2.   begin
  3.     {...}
  4.   end {<- no ";" here!}
  5. else
  6.     {...};

The sintax of "if ... else" is much more strict (and demostrative) in this sense.
« Last Edit: June 19, 2021, 08:05:04 am by lucamar »
Turbo Pascal 3 CP/M - Amstrad PCW 8256 (512 KB !!!) :P
Lazarus/FPC 2.0.8/3.0.4 & 2.0.12/3.2.0 - 32/64 bits on:
(K|L|X)Ubuntu 12..18, Windows XP, 7, 10 and various DOSes.

440bx

  • Hero Member
  • *****
  • Posts: 2443
Re: It has a little bug in IDE
« Reply #5 on: June 19, 2021, 08:20:11 am »
The sintax of "if ... else" is much more strict (and demostrative) in this sense.
Yes, it is because since neither the "end" nor the "else" keywords are statements a semicolon in between won't be welcome. :)
FPC v3.0.4 and Lazarus 1.8.2 on Windows 7 64bit.

y.ivanov

  • Full Member
  • ***
  • Posts: 197
Re: It has a little bug in IDE
« Reply #6 on: June 19, 2021, 11:34:42 am »
The sintax of "if ... else" is much more strict (and demostrative) in this sense.
Yes, it is because since neither the "end" nor the "else" keywords are statements a semicolon in between won't be welcome. :)
In fact, "end" is a statement, or at least, it is the end of a compound statement.

Let me humbly explain.
The "statement" is a non-terminal into the formal grammar of Pascal. The word "end" is a terminal used at the end of another non-terminal named "compound statement".
Code: [Select]
<compound statement> ::= begin <statement> {; <statement> } end The if statement is defined as:
Code: [Select]
<if statement> ::= if <expression> then <statement> | if <expression> then <statement> else <statement>There is no semicolon before the "else" terminal.

Formally defined in that way, you can put semicolons between two "end"s and it will prefix an empty statement.
Code: Pascal  [Select][+][-]
  1. if Cond then begin
  2.   begin
  3.   end ; {empty statement}
  4.   ; {empty statement}
  5.   ;;;;;;;;;;;;;
  6. end

And this is not an error or feature, this is by design.

Requiring semicolon between the statement and the "else" keyword (as it is in our beloved C) will put the Pascal grammar in another class - the class that cannot be parsed without backtracking.

Edit: but actually the OP was for the IDE not for the Pascal syntax.
« Last Edit: June 19, 2021, 11:36:39 am by y.ivanov »

MarkMLl

  • Hero Member
  • *****
  • Posts: 2875
Re: It has a little bug in IDE
« Reply #7 on: June 19, 2021, 12:23:43 pm »
That is not a bug.

Pascal has allowed that syntax since the 1980's.

cheers
S.

Others have remarked on this but I want to emphasise a point: Pascal (from the early 1970s), and ALGOL before it (from the late 1950s), were *DEFINED* as using ; as a separator, not as a terminator. Most compilers *PERMIT* a *SUPERFLUOUS* ; where it doesn't introduce problems.

MarkMLl
Turbo Pascal v1 on CCP/M-86, multitasking with LAN and graphics in 128Kb.
Pet hate: people who boast about the size and sophistication of their computer.
GitHub repositories: https://github.com/MarkMLl?tab=repositories

440bx

  • Hero Member
  • *****
  • Posts: 2443
Re: It has a little bug in IDE
« Reply #8 on: June 19, 2021, 04:16:17 pm »
In fact, "end" is a statement, or at least, it is the end of a compound statement.
As you pointed out, it is a keyword in the pair that defines a compound statement but, "end" itself is not a statement.

Let me humbly explain.
Your explanation is good but misleading because "end" is not a statement.  When the compiler looks for a statement (because it expects one), it looks for keywords such as "for", "while", "repeat", "begin", etc but, there is definitely no "end" in the list of possible statements.

The word "end" is a terminal used at the end of another non-terminal named "compound statement".
Code: [Select]
<compound statement> ::= begin <statement> {; <statement> } end
what you stated there is absolutely correct and note that the definition of <statement> does not include "end".  The <begin><end> pair are compound statement (a statement list if you prefer) delimiters.  The pair, _together_ is a statement, a compound statement to be more precise, that starts with the keyword "begin" (which without a matching "end" isn't a statement either).  "end" by itself is _not_ a statement, it doesn't even start a statement.

Requiring semicolon between the statement and the "else" keyword (as it is in our beloved C) will put the Pascal grammar in another class - the class that cannot be parsed without backtracking.
It would make the semicolon a statement terminator instead of separator.  I don't think that would make backtracking necessary (at least I don't see a case where the presence of a semicolon would make it necessary at this time.)
FPC v3.0.4 and Lazarus 1.8.2 on Windows 7 64bit.

y.ivanov

  • Full Member
  • ***
  • Posts: 197
Re: It has a little bug in IDE
« Reply #9 on: June 19, 2021, 05:58:57 pm »
In fact, "end" is a statement, or at least, it is the end of a compound statement.
As you pointed out, it is a keyword in the pair that defines a compound statement but, "end" itself is not a statement.
It's my bad wording, the "end" is a terminal symbol in the sense of the BNF notation. Considering we are discussing the "if" statement, the preceding non-terminal symbol of "else" can be a "statement" (that is by Pascal definition rules). The only "statement" non-terminal which ends on an "end" terminal symbol is a "compound statement". In other words, that particular "end" ends a compound statement.

Let me humbly explain.
Your explanation is good but misleading because "end" is not a statement.  When the compiler looks for a statement (because it expects one), it looks for keywords such as "for", "while", "repeat", "begin", etc but, there is definitely no "end" in the list of possible statements.
The compiler doesn't look for a statement. It takes the next lexeme and tries to follow its current production rule.

The word "end" is a terminal used at the end of another non-terminal named "compound statement".
Code: [Select]
<compound statement> ::= begin <statement> {; <statement> } end
what you stated there is absolutely correct and note that the definition of <statement> does not include "end".  The <begin><end> pair are compound statement (a statement list if you prefer) delimiters.  The pair, _together_ is a statement, a compound statement to be more precise, that starts with the keyword "begin" (which without a matching "end" isn't a statement either).  "end" by itself is _not_ a statement, it doesn't even start a statement.
On the contrary: definition of statement includes the "end". The BNF rules are too many to include here, but the "statement" non-terminal definition is a recursive one, like:
Code: [Select]
<statement> ::= <simple statement> | <if statement> | ... | <compound statement>Note <statement> includes <compound statement> and also <compound statement> includes <statement>.

Requiring semicolon between the statement and the "else" keyword (as it is in our beloved C) will put the Pascal grammar in another class - the class that cannot be parsed without backtracking.
It would make the semicolon a statement terminator instead of separator.  I don't think that would make backtracking necessary (at least I don't see a case where the presence of a semicolon would make it necessary at this time.)
The separator is a term of the lexer. (What is a terminator?) The separators are whitespace and comments, they separate the lexemes. The semicolon is a terminal symbol in the BNF rules.

Putting a semicolon there will change the grammar from LL(1) to LL(k), k>1. AFAIK, the FPC compiler uses a recursive descent parser, which is the main reason of its speed. Such a parser will need to backtrack if it can't decide which production rule to follow by just one lexeme (k>1).

440bx

  • Hero Member
  • *****
  • Posts: 2443
Re: It has a little bug in IDE
« Reply #10 on: June 19, 2021, 06:29:24 pm »
The only "statement" non-terminal which ends on an "end" terminal symbol is a "compound statement". In other words, that particular "end" ends a compound statement.
yes but, "end" does _not_ start a statement.

The compiler doesn't look for a statement. It takes the next lexeme and tries to follow its current production rule.
The compiler better look for a statement, that's what tells the compiler the next production to execute.  When the compiler sees a "begin" it looks for a statement which must be anyone of the symbols that start a statement of which "end" is _not_ one of them.

On the contrary: definition of statement includes the "end". The BNF rules are too many to include here, but the "statement" non-terminal definition is a recursive one, like:
Code: [Select]
<statement> ::= <simple statement> | <if statement> | ... | <compound statement>Note <statement> includes <compound statement> and also <compound statement> includes <statement>.
Notice that in that BNF rule, there is no statement that starts with "end".  "end" is part of a compound statement but, it is _not_ a token that starts a statement.  It is neither found in <simple statement> nor in the start of <compound statement> or any other statement for that matter.  "end" is not a statement, it is a statement list delimiter.

The separator is a term of the lexer. (What is a terminator?) The separators are whitespace and comments, they separate the lexemes. The semicolon is a terminal symbol in the BNF rules.
The semicolon is a terminal symbol but, _how_ it's used is what makes it a separator instead of a terminator.  if the semicolon was a _terminator_ then the <statement> production would include the semicolon in it, instead in Pascal it appear in a production such as { statement } { ";" statement } if it were a terminator a statement list would specify statement as { statement ";" }.  That is what makes the semicolon a terminator (as in C)

Putting a semicolon there will change the grammar from LL(1) to LL(k), k>1.
I cannot think of an instance where that would be the case.  There is no reason for the compiler to have to backtrack because a semicolon terminates statements instead of separating them.

AFAIK, the FPC compiler uses a recursive descent parser, which is the main reason of its speed. Such a parser will need to backtrack if it can't decide which production rule to follow by just one lexeme (k>1).
FPC is a recursive descent compiler but, changing the semicolon from separator to terminator wouldn't affect that.  It would affect the grammar but, it wouldn't create a situation where the compiler would have to backtrack (at least not in Pascal.)
FPC v3.0.4 and Lazarus 1.8.2 on Windows 7 64bit.

y.ivanov

  • Full Member
  • ***
  • Posts: 197
Re: It has a little bug in IDE
« Reply #11 on: June 19, 2021, 09:38:24 pm »
yes but, "end" does _not_ start a statement.
Have I ever said the opposite?

The compiler better look for a statement, that's what tells the compiler the next production to execute.  When the compiler sees a "begin" it looks for a statement which must be anyone of the symbols that start a statement of which "end" is _not_ one of them.
The recursive descent parser usually is implemented as recursive procedures which closely resembles the BNF non-terminal rules. Those procedures uses the next seen terminal symbol to decide which rule to follow (procedure to call).  And BTW, the "end" is perfectly valid to follow "begin".

On the contrary: definition of statement includes the "end". The BNF rules are too many to include here, but the "statement" non-terminal definition is a recursive one, like:
Code: [Select]
<statement> ::= <simple statement> | <if statement> | ... | <compound statement>Note <statement> includes <compound statement> and also <compound statement> includes <statement>.
Notice that in that BNF rule, there is no statement that starts with "end".  "end" is part of a compound statement but, it is _not_ a token that starts a statement.  It is neither found in <simple statement> nor in the start of <compound statement> or any other statement for that matter.
Again, did I ever said the opposite?

  "end" is not a statement, it is a statement list delimiter.
No. "end" is definitely not a delimiter. It is a terminal symbol which stands at the end of the <compound statement> rule (and some others too).

The separator is a term of the lexer. (What is a terminator?) The separators are whitespace and comments, they separate the lexemes. The semicolon is a terminal symbol in the BNF rules.
The semicolon is a terminal symbol but, _how_ it's used is what makes it a separator instead of a terminator.
I see. You named it (as separator, terminator) according to when it appears to be between or at the end of the "list". I would name it "promoter" instead, because if you look closer into the <compound statement> rule, you'll see that this is the token that tells the parser that another statement will follow, even it is the empty statement. Don't confuse yourself with that it is usually the last symbol on the line.

if the semicolon was a _terminator_ then the <statement> production would include the semicolon in it, instead in Pascal it appear in a production such as { statement } { ";" statement } if it were a terminator a statement list would specify statement as { statement ";" }.  That is what makes the semicolon a terminator (as in C)
This definition { statement ";" } will introduce ambiguity which changes grammar to LL(k). This is why you can't parse C grammar with a (naive) recursive descent parser.

I cannot think of an instance where that would be the case.  There is no reason for the compiler to have to backtrack because a semicolon terminates statements instead of separating them.
Consider the following simple example: the if statement is being parsed, after the "then" token the if_rule procedure has called the statement_rule procedure.  The statement_rule procedure returns consuming the semicolon. Now what to expect? Another semicolon because "if" is also a statement (and must be terminated)? "else" because there is an else clause? or some other statement?  You can't tell for sure that the current if_rule is completed or not. You must take a decision and eventually to backtrack if it was wrong.
 

MarkMLl

  • Hero Member
  • *****
  • Posts: 2875
Re: It has a little bug in IDE
« Reply #12 on: June 19, 2021, 10:32:36 pm »
I'm not sure whether the "terminal" and "non-terminal" concepts had been formalised when Wirth "migrated" (hurriedly, according to my research) from ALGOL-W to Pascal, and this might contribute to some of the sloppiness highlighted by the current discussion. In any event, Wirth's early compilers were table-driven recursive /ascent/, and I think we have to stick to the BNF and "railroad diagrams" of the era rather than trying to impute deeper structure.

Apart from that I'd observe that this discussion is substantially more "nerdish" than helps the OP.

MarkMLl
Turbo Pascal v1 on CCP/M-86, multitasking with LAN and graphics in 128Kb.
Pet hate: people who boast about the size and sophistication of their computer.
GitHub repositories: https://github.com/MarkMLl?tab=repositories

y.ivanov

  • Full Member
  • ***
  • Posts: 197
Re: It has a little bug in IDE
« Reply #13 on: June 19, 2021, 10:53:34 pm »

Apart from that I'd observe that this discussion is substantially more "nerdish" than helps the OP.

Good point. It is written in the subject: it is about the IDE.
Maybe it must be discussed elsewhere.

Thanks,

MarkMLl

  • Hero Member
  • *****
  • Posts: 2875
Re: It has a little bug in IDE
« Reply #14 on: June 19, 2021, 11:12:27 pm »
Good point. It is written in the subject: it is about the IDE.
Maybe it must be discussed elsewhere.

Although in fairness, OP is ascribing behaviour to the IDE which is really down to the syntax of the language and the strictness of the compiler.

Hopefully he's got the message without being discouraged :-)

I'd throw in a couple of related points before this discussion completely winds down. First, at least some of the ALGOL implementations describe anything after END as being an implicit comment, with minimal consideration of the status of ; in that context. Second, the END. at the end of an ALGOL (hence Pascal) program was a non-standard "hack" from Burroughs that allowed the compiler to decide that it had seen enough without reading the next card which would potentially have screwed up the remainder of the batch job (and their compilers insist that nothing follow it).

I've spent a bit of time over the last few weeks looking at Verilog and VHDL, and it's an interesting exercise speculating which bits are unarguably ALGOL, which bits are unarguably Ada, and which bits are probably Ada but the sub-sub-sub-committee had their own idea about the END behaviour and didn't agree with the guys in the next office :-)

MarkMLl
Turbo Pascal v1 on CCP/M-86, multitasking with LAN and graphics in 128Kb.
Pet hate: people who boast about the size and sophistication of their computer.
GitHub repositories: https://github.com/MarkMLl?tab=repositories

 

TinyPortal © 2005-2018