Path: utzoo!mnetor!uunet!lll-winken!lll-tis!ames!ncar!oddjob!nucsrl!accuvax.nwu.edu!morrison From: morrison@accuvax.nwu.edu.UUCP (Vance Morrison ) Newsgroups: comp.lang.c++ Subject: Re: Proposal for Exceptions for C++ Message-ID: <8180002@accuvax.nwu.edu.UUCP> Date: 30 Mar 88 17:28:44 GMT References: <8180006@eecs.nwu.edu> Organization: Northwestern U, Evanston IL, USA Lines: 169 This is in response to the comments I have seen so far on my proposal for exception handling for C++. First may I say that I am glad to see such a good response so soon. Second, I really must apologize for the incompleteness of my proposal. I realize that I really did not explain the semantics of the stack unwinding and other issues well (if at all). Instead I am relying on the interactive nature of the net to fill in the gaps as necessary. Here are some things that need clarification MEANING OF RAISING AN EXCEPTION First let me clarify what happens when an exception is raised. In my model a search goes on for the most closely nested 'catch' statement that protects the code in which the exception was raised.t The 'catch' clause is given control and unless the catch is exited (by using a 'return' 'goto' 'break' or 'resume' statement), the exception is implicitly reraised. This causes a search for the next layer of 'catch'ing until either a catch clause is exited or the last chance handler is executed. MEANING OF RESUME There is come confusion about the meaning of 'resume'. Resume returns control to the statement after the 'catch' clause, NOT TO THE POINT WHERE THE EXCEPTION WAS RAISED! For example these two structures are equivalent i=j/k; catch { printf("error"); resume; } printf("done"); is equivalent to i=j/k; catch { printf("error"); goto out; } out: printf("done"); MY RESPONSE TO COMMENTS: Here I will respond to some comments I have seen, If I misrepresent anyone, I am sorry, please let me know. IN RESPONSE TO LARRY YAFFE'S COMMENTS: Larry Yaffe is concerned that my proposal does not allow restart capability (that is the ability to continue from the point at which the exception occurred). In response may I say 1) My proposal does NOT exclude the possibility of adding a restart capability. By adding a keyword 'restart' (or whatever) it could be added. 2) Second, I have found personally, that restart capability is not indispensable, and usually not very useful. Usually, you want to restart the problem from the beginning if a fatal error occurs, and if you want the restart from the middle, you can always pass back state information so that the procedure can be called "in the middle", (I can provide an example if you like). 3) Because the exception was raised, the procedure is telling you that it cannot continue normally. Therefore the handler must "fix" the problem before it can continue. Providing mechanisms for this is a nasty problem. 4) Restart is quite a bit more complicated to implement, since destructors CANNOT be called until you can be sure a restart is not pending. In general its a mess. I have found personally that exceptions without restart are QUITE useful, so we should implement that first. If we find we need restart, we can add it as an option. IN RESPONSE TO NEVIN LIBER'S COMMENTS Nevin Had several comments, the first of which was to question my reasoning on the default '_raise' at the end of a 'catch' statement. This is a very important point, and I would like to clarify it. First the '_raise' an 'catch' statements are really just tools for building "real exceptions" and although '_raise' and 'catch' only implement a single unnamed exception, it is easy to extend as I have done to provide Named exceptions. Thus a 'catch' clause will almost always have the form catch { if (is_raised(EXCEPTION1) { resume; } else if(is_raised(EXCEPTION2) { resume; } } That is I am only prepared to handle certain exceptions I know about (or groups of exceptions, or exceptions with certain attributes), The rest I don't know how to handle so I should pass them on to someone who does (by reraising). The alternative is that the programmer must explicitly reraise the exception. The code would look like catch { if (is_raised(EXCEPTION1) { } else if(is_raised(EXCEPTION2) { } else _raise; } Now if the programmer forgot to put the _raise, he is implicitly ignoring all errors he can't handle. THAT IS JUST THE PROBLEM I WANT TO SOLVE. The problem with return codes is that the are all to easy to ignore, and numerous bugs and cryptic program crashes are the result. The beauty of exceptions is that the default action for an exception is defined by the module designer and unless the module user EXPLICITLY catches the exception, that default action is taken. Nevin also did not like my binding in the case of for(i=0; i<10; i++) printf("test\n"); catch { printf("error"); } The question is does catch protect just the printf or the entire for statement. I defined it to be just the printf (that is catch binds to the smallest statement). In some ways this is an arbitrary decision, but I believe that this binding is the more common, so is a better choice. Finally Niven felt that Exceptions that I define have little advantage over return codes. He obviously hasn't used them (:-). Part of the problem is my example was trivial The big advantages in my opinion are: 1) Exceptions can travel up more that one stack frame, so that you don't need code like the fragment below every time you call a function ret = some_function(); if (ret != SUCCESS) return(ret); 2) If a programmer uses a module, IF HE DOES NOTHING errors will be handled in a default way (ie printed out). With error codes, the default action is it ignore the error. 3) Exceptions can easily have parameters, a BIG plus. **************************************************************************** Nevin has asked for an implementation of my exception handling. I do indeed have an all the major parts of an implementation. This implementation is a preprocessor for C++ that uses 'asm()' statements into the code at proper places which leave lables for the boundaries of protected regions. But that is not the point of my proposal, There are many implementation of exception handling that could be used. What I want to establish the syntax for the end result. Thats all for now. Vance Morrison