Thread overview
BUG: Break within While Statement with Try/Catch Inside
Jul 12, 2004
John Reimer
Re: Break within While Statement with Try/Catch Inside
Jul 12, 2004
Kris
Jul 14, 2004
John Reimer
Jul 14, 2004
Walter
Jul 16, 2004
David Medlock
Jul 16, 2004
John Reimer
July 12, 2004
The D Programming Language manual states:

"break exits the innermost enclosing while, for, do, or switch statement, resuming execution at the statement following it."

There appears to be a bug in which "break" does not exit the enclosing "while" if the "break" is within a try{} statement.  Example:

==================================================
import std.stdio;

int main() {
        while (true) {
                try {
                if (true)
                        break;
                } catch (Object e) {
                if (true)
                        break;
                }
        }
        writefln("Exiting main successfully");
        return 0;
}
=================================================

The first "break" causes a continuation of the while loop rather than an exit of the while loop.  The last writefln() never gets executed.

Apparently the same problem does NOT exist in the "catch" statement as the following code reveals:

==================================================
import std.stdio;

int main() {
        while (true) {
                try {
                throw new Object;
                } catch (Object e) {
                if (true)
                        break;
                }
        }
        writefln("Exiting main successfully");
        return 0;
}
=================================================

In this instance the "break" in the catch statement actually exits the "while" loop correctly.

This was a difficult bug to track down.  Needs fixing me thinks!

Later,

John
July 12, 2004
"John Reimer" <brk_6502@NO_SPA_M.yahoo.com> wrote in message news:cct6f0$cj6$1@digitaldaemon.com...
> The D Programming Language manual states:
>
> "break exits the innermost enclosing while, for, do, or switch statement, resuming execution at the statement following it."
>
> There appears to be a bug in which "break" does not exit the enclosing "while" if the "break" is within a try{} statement.  Example:
>
> ==================================================
> import std.stdio;
>
> int main() {
>         while (true) {
>                 try {
>                 if (true)
>                         break;
>                 } catch (Object e) {
>                 if (true)
>                         break;
>                 }
>         }
>         writefln("Exiting main successfully");
>         return 0;
> }
> =================================================
>
> The first "break" causes a continuation of the while loop rather than an exit of the while loop.  The last writefln() never gets executed.
>
> Apparently the same problem does NOT exist in the "catch" statement as the following code reveals:
>
> ==================================================
> import std.stdio;
>
> int main() {
>         while (true) {
>                 try {
>                 throw new Object;
>                 } catch (Object e) {
>                 if (true)
>                         break;
>                 }
>         }
>         writefln("Exiting main successfully");
>         return 0;
> }
> =================================================
>
> In this instance the "break" in the catch statement actually exits the "while" loop correctly.
>
> This was a difficult bug to track down.  Needs fixing me thinks!

Yeah, I'll second that.

It was wildly unexpected, most frustrating, and totally bogus all at the same time. The natural reaction is to blame anything *but* the compiler, which wasted the efforts of several in this instance. Here's what actually happened:

1) segfault in linux running mango test cases
2) lots of incremental isolation of code in various scattered places to see
what might be the cause
3) some honing in upon a SocketListener which executes as an independent
thread waiting for socket input
4) more time spent isolating code in a series of misguided attempts to
figure out why linux sockets or threads are being a total pain
5) segfault noted in gcx.d indicated the heap is corrupted (whoopee)
6) even more effort wasted trying various wild goose chases, and
constructing equivalence tests on Win32
7) eventual realization that the break; statement does absolutely nothing,
zero, zilch, sweet fuck all, when executed within a try{} block (surrounded
by an outer while).

Hear ye, the seven deadly sins of working with Beta code ... that bogus codegen caused a socket to be read yet again after the OS had interrupted it because the host program was exiting. This caused some layer of socket.read() to trash part of the heap, causing gcx.d to segfault during termination cleanup. All reasonable efforts in the client code to avoid this situation were badly mauled by the lack of a logical execution path, due to the flaccid break statement.

Times like this ..... ..... .....






July 14, 2004
Sooo... Walter, is this something you are going to fix in the next release?
July 14, 2004
"John Reimer" <brk_6502@NO_SPA_M.yahoo.com> wrote in message news:cd2cks$309g$1@digitaldaemon.com...
> Sooo... Walter, is this something you are going to fix in the next
release?

I guess people don't like having a 'break' out of a try block.


July 16, 2004
Walter wrote:
> "John Reimer" <brk_6502@NO_SPA_M.yahoo.com> wrote in message
> news:cd2cks$309g$1@digitaldaemon.com...
> 
>>Sooo... Walter, is this something you are going to fix in the next
> 
> release?
> 
> I guess people don't like having a 'break' out of a try block.
> 
> 
Perhaps a 'break while;' statement similar to named break which would still allow leaving a try block?

On second thought that seems a bit like extra baggage.....
July 16, 2004
David Medlock wrote:
> Walter wrote:
> 
>> "John Reimer" <brk_6502@NO_SPA_M.yahoo.com> wrote in message
>> news:cd2cks$309g$1@digitaldaemon.com...
>>
>>> Sooo... Walter, is this something you are going to fix in the next
>>
>>
>> release?
>>
>> I guess people don't like having a 'break' out of a try block.
>>
>>
> Perhaps a 'break while;' statement similar to named break which would still allow leaving a try block?
> 
> On second thought that seems a bit like extra baggage.....

I do not see why we need a "break" from a try block.  If it stays in the language, then it will be impossible to get out of an enclosing while loop apart from a "return" or a labeled "break."  A return is not always what is desired, and a goto is a hackish thing to be stuck with in such a situation.

But that's beside the point, breaking from a try block is not part of the language definition.  The documentation is clear about the 4 situations in which the break is effective: while, for, do, and switch statements. "break" should stay true to it's original definiton.

Maybe the try/break was supposed to be a handy little sercret feature.  But, if it is, it's sure a mean trick to play on the unsuspecting programmer.