Recent

Author Topic: Case statement does not handle all possible cases  (Read 6913 times)

Zoran

  • Hero Member
  • *****
  • Posts: 1671
    • http://wiki.lazarus.freepascal.org/User:Zoran
Case statement does not handle all possible cases
« on: June 19, 2021, 06:54:22 pm »
When compiling my programs with FPC from trunk, the compiler gives a lot of warnings:
Quote
Warning: Case statement does not handle all possible cases

Isn't it quite normal programming practice, to do something in some cases, without covering all possible values from some enumeration?

Why should a programmer be warned to cover all possible cases?

Kays

  • Sr. Member
  • ****
  • Posts: 334
  • Whasup!?
    • KaiBurghardt.de
Re: Case statement does not handle all possible cases
« Reply #1 on: June 19, 2021, 07:08:37 pm »
Why should a programmer be warned to cover all possible cases?
It is an ISO requirement. ISO 7185, § 6.8.3.5 “Case-statements”
Quote
One of the case-constants shall be equal to the value of the case-index upon entry to the case-statement; otherwise, it shall be an error
Now an “error” is a
Quote
violation by a program of the requirements of the requirements to this International Standard that a processor is permitted to leave undetected.
In other words, an “error” may produce just a warning as the FPC [trunk version] does now. This becomes more apparent by the wording of ISO 10206 (“Extended Pascal”), § 6.9.3.5 “Case-statements”, which says “dynamic violation” (cf. § 3.1).

Isn't it quite normal programming practice, to do something in some cases, without covering all possible values from some enumeration?
I think it was TP that introduced the else-clause and the possibility of a fall-through/bypassed case-statement. For Delphi-compatibility the FPC adopted this malpractice. Pascal is very well designed and there are reasons why all possible case-labels have to appear in case-statements.
Yours Sincerely
Kai Burghardt

winni

  • Hero Member
  • *****
  • Posts: 2507
Re: Case statement does not handle all possible cases
« Reply #2 on: June 19, 2021, 07:13:48 pm »
I think it was TP that introduced the else-clause and the possibility of a fall-through/bypassed case-statement. For Delphi-compatibility the FPC adopted this malpractice. Pascal is very well designed and there are reasons why all possible case-labels have to appear in case-statements.

Hi!

TP did not invent the else-clause for the case statement. The misstreated it.

The original syntax for Pascal is:
Code: Pascal  [Select][+][-]
  1. Case i of
  2. 1: .....;
  3. 2: ....;
  4. otherwise ....:
  5. end;


fpc knows the original syntax.

Winni

Zoran

  • Hero Member
  • *****
  • Posts: 1671
    • http://wiki.lazarus.freepascal.org/User:Zoran
Re: Case statement does not handle all possible cases
« Reply #3 on: June 19, 2021, 07:23:00 pm »

Thank you, Kays.

However, for decades, FPC, Delphi and TP programmers have been very used to case statements without covering all possible values.

Perhaps the warning should be issued in iso mode only?

Bart

  • Hero Member
  • *****
  • Posts: 4351
    • Bart en Mariska's Webstek
Re: Case statement does not handle all possible cases
« Reply #4 on: June 19, 2021, 09:57:36 pm »
If it bothers you filter it out using the appropriate -vmxxxx in your fpc.cfg?

E.g. I have this in my fpc.cfg
Code: [Select]
#Don't show the "function X; marked as inline is not inlined" warning
-vm6058
Because I don't bother.

Bart

MarkMLl

  • Hero Member
  • *****
  • Posts: 2869
Re: Case statement does not handle all possible cases
« Reply #5 on: June 19, 2021, 10:45:14 pm »

Thank you, Kays.

However, for decades, FPC, Delphi and TP programmers have been very used to case statements without covering all possible values.

Perhaps the warning should be issued in iso mode only?

"I hear what you're saying", but as a refugee from Modula-2 I'm entirely happy with ensuring that every case has an otherwise clause irrespective of whether the selector is a small enumeration or a larger arbitrary integer or cardinal type.

My own feeling is that coverage should be complete if the selector is an enumeration, but that it might arguably be relaxed if it is a numeric type. In practice that distinction might not be easy or desirable to make, in which case a compiler should err on the side of caution.

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

nanobit

  • Full Member
  • ***
  • Posts: 112
Re: Case statement does not handle all possible cases
« Reply #6 on: June 20, 2021, 03:45:53 am »
I think it was TP that introduced the else-clause and the possibility of a fall-through/bypassed case-statement. For Delphi-compatibility the FPC adopted this malpractice. Pascal is very well designed and there are reasons why all possible case-labels have to appear in case-statements.

For exactness it should be noted here that "else" in FPC has a different meaning than "else" in Delphi, C++, C#.
The latter languages implement "all other values of underlying type", FPC implements only "all other defined values".
https://bugs.freepascal.org/view.php?id=36983

speter

  • Full Member
  • ***
  • Posts: 217
Re: Case statement does not handle all possible cases
« Reply #7 on: June 20, 2021, 04:02:21 am »
The discussion above prompted me to look at my old pascal code. I found (to my surprise) that Microsoft's Pascal compilers used else...otherwise (I used v3.13, v3.31 & v4). I had totally forgotten about using "otherwise" with Microsoft's compilers.

I also found a program I wrote in 1989 to convert my 'old' pascal code to the Turbo Pascal dialect; that included substituting "else" for "otherwise". :)

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)

PascalDragon

  • Hero Member
  • *****
  • Posts: 3191
  • Compiler Developer
Re: Case statement does not handle all possible cases
« Reply #8 on: June 20, 2021, 11:50:26 am »
However, for decades, FPC, Delphi and TP programmers have been very used to case statements without covering all possible values.

Perhaps the warning should be issued in iso mode only?

No, because enumerations type in FPC do behave differently from those in Delphi and TP and they already did so before the warning thus potentially leading to bugs for people. Which was why the warning was introduced (and not because ISO required it, though there it's of course welcome as well).

As nanobit mentioned, if you have an enum with holes then only those values that are indeed defined are considered valid, thus it is valid for the compiler to exploit this behavior for optimizations which might lead to unexpected results for the developer if they didn't adhere to the warning.

Jonas Maebe

  • Hero Member
  • *****
  • Posts: 884
Re: Case statement does not handle all possible cases
« Reply #9 on: June 20, 2021, 12:14:25 pm »
As nanobit mentioned, if you have an enum with holes then only those values that are indeed defined are considered valid, thus it is valid for the compiler to exploit this behavior for optimizations which might lead to unexpected results for the developer if they didn't adhere to the warning.
No, the values within "holes" are defined. It's values < low(enumtype) or > high(enumtype) that are undefined. It's also not just for "case", but for any expression. E.g. the compiler will also optimise away comparisons like "if enumval < low(enumtype) then ..." (with a warning about unreachable code), and will never insert range checks for "arr[enumval]" in case "arr" is defined as an "array[enumtype]". Delphi does the same for array indexing for some reason, even though for the rest it indeed generally handles enums like C rather than like Pascal.

Also, in ISO modes this warning is in fact an error.

nanobit

  • Full Member
  • ***
  • Posts: 112
Re: Case statement does not handle all possible cases
« Reply #10 on: June 20, 2021, 01:20:35 pm »
Jonas, I added a note about why we can improve the case-statement regardless of other expressions. https://bugs.freepascal.org/view.php?id=36983

Jonas Maebe

  • Hero Member
  • *****
  • Posts: 884
Re: Case statement does not handle all possible cases
« Reply #11 on: June 20, 2021, 01:32:34 pm »
Programming languages are based on consistency. All statements must abide by the same rules regarding a particular type, otherwise you have to program with the language reference manual next to you so you can look up for each expression/statement how it bahaves.

Either an enum is either only defined between min and max (ISO Pascal, FPC, Java), or it's defined as long as it fits in the underlying type (C, C++, C#). Delphi is buggy in this regard: it treats array accesses like FPC and the rest like C/C++/C#.


nanobit

  • Full Member
  • ***
  • Posts: 112
Re: Case statement does not handle all possible cases
« Reply #12 on: June 20, 2021, 02:10:23 pm »
Ok, then we disagree about this.
I agree with you on the definedness (min, max),
but not the conclusions about how to handle the undefined values.

Jonas Maebe

  • Hero Member
  • *****
  • Posts: 884
Re: Case statement does not handle all possible cases
« Reply #13 on: June 20, 2021, 02:21:38 pm »
"Undefined" literally means that the compiler does not and cannot guarantee any particular kind of handling. To have that, you have to make such behaviour defined (like C and C++ do).

 

TinyPortal © 2005-2018