iiitsh@cybaswan.UUCP (Steve Hosgood) (08/09/89)
Netreaders will remember my original article a week or so ago that discussed adding the ability for C functions to return unambiguous error indications without all the problems currently encountered. I've been well pleased with the replies I've read. Below are my answers to some of the comments I've seen. > From: pardo@june.cs.washington.edu (David Keppel) > Date: 4 Aug 89 17:09:21 GMT > Organization: University of Washington, Computer Science, Seattle > Lines: 16 > > iiitsh@cybaswan.UUCP (Steve Hosgood) writes: > >[errval(foo())] > > Until it is `prior art', it probably doesn't belong in dpANS C. > > Often, `-1' is used as a return value for things that can be array > indicies, because `-1' can't be an array index. Having `errval' > requires that you know not just the return type, but also which kinds > of values are going to be meaningful (since, e.g., not all compilers > have condition codes). To do this `right', you need a stronger typing > system than C provides. > My 'errval' macro that checks for 'x < 0' or possibly 'x == 1' was intended as a way for users with older compilers without the proposed feature to 'fake' it fairly easily. Obviously, you have no type-checking with a macro, and you're reliant on the actual return value to tell you there's an error, so the macro you use will often have to be tailored to the function that you called. 'Errval' (or whatever) *must* be implemented by the compiler so as to work properly. > From: siebren@piring.cwi.nl (Siebren van der Zee) > From: david@psitech.UUCP (david Fridley) > Date: 5 Aug 89 20:41:45 GMT > Organization: PsiTech Inc., Fountain Valley, CA > > Wouldn't it be nice if you could return more than one value from a C function? > ie: > (ret1,ret2)=func(param1,param2,param3); > I believe this would solve error problems, and many others that I have had. > I've often though about this, but can't think up a sensible methodology. The idea of passing a boolean WIN/LOSE flag along with the normal return value is managable (I think), let's see if anyone out there can come up with a multiple return value scenario. Oh, and don't use a comma to seperate the multiple targets of the assignment - comma is already used for other things, and we can't have a context sensitive grammar! See later. > Date: 4 Aug 89 19:40:24 GMT > Organization: CWI, Amsterdam > > Ok, and now the hard part: what should the code from the > CALLED function look like? > Oops, I left that out of the posting! Sorry. Actually, Henry Spencer's posting and my reply just about answer this question - read on. > From: henry@utzoo.uucp (Henry Spencer) > Date: 5 Aug 89 22:33:31 GMT > Organization: U of Toronto Zoology > > In article <8314@boring.cwi.nl> siebren@piring.cwi.nl (Siebren van der Zee) writes: > >>[errval(foo())] > >Ok, and now the hard part: what should the code from the > >CALLED function look like? > > The obvious thing to do is to have two different kinds of "return" statement, > one for normal and one for errors. That completely hides how the "error" > flag is passed back. Unfortunately, it is awkward on some machines, where > there are no condition codes. > As I said above, I forgot to mention this bit in my posting. Two different return statements would do the trick, but I'd rather see a way of passing the 'error' flag from a variable. I'd like to see any extension involve the least number of new reserved-words - this proposal requires 'ereturn' or something similar to be reserved. Also, I consider it neater to have my routines terminate in a single 'return' statement, and having to use two differnt types of 'return' in order to pass the 'error' flag rather precludes this. So: maybe something like ... return val, err; ..would do the trick. I don't seriously want to use a comma seperator though, as it's already used for other things. Trouble is, I can't think of any other unused seperator. The guy (see above) who proposed the more general multiple value return mechanism used commas too. Better find another symbol. Double colon might work - but I think that's used by C++ and that could cause problems if 'C' started to employ it too. Let's see: ... return val::errflag; ..seen worse, though C++ boys will be hammering on the door any minute now!. > Interested parties, note: the idea is *guaranteed* to go nowhere unless > you are interested enough to implement it in a compiler. > -- ..yeah, but if you implement such a concept in a compiler, you've just put an extension into it, and that would start to undo all the standards effort straight away. I hate 'extended' languages - DEC and HP are my least favorite language vendors for this very reason. It's all a bit 'chicken and egg' if ANSI won't consider it until someone implements it. > From: mwm@eris.berkeley.edu (Mike (I'll think of something yet) Meyer) > Date: 5 Aug 89 04:46:49 GMT > Organization: Missionaria Phonibalonica > > How about: > > #define errval(x) (errno = 0, (x), errno) > > It'll even work on the current standard. Whether you can get this to > turn into tweaks to the carry flag (I hope that nobody would advocate > referring to hardware flags in the standard; there's already hardware > that C runs on without such flags) in a standard-conforming compiler > is an interesting question. > I agree, the standards mustn't refer to the 'carry' flag. Chances are that many implementors would use the carry flag though - if there is one on the hardware. > From: gregg@cbnewsc.ATT.COM (gregg.g.wonderly) > Date: 6 Aug 89 22:38:46 GMT > Organization: AT&T Bell Laboratories > > I have always liked the idea of having the types of information that VMS > provides in condition codes. All I'm trying to suggest is a method for giving the caller of a C-routine the information that a failure occurred. Once he knows that it failed he can go find out the real reason. Often that will be to check the actual return value, or possible the 'errno' external variable. What Gregg's doing (I think) is proposing a more powerful 'errno' variable. I *think* this a parallel thread. Redefining 'errno' requires no changes to 'C' - just a change in accepted procedure by the writer and users of standard library routines. To be honest - I dislike the VMS approach... too heavy, man! > From: peter@ficc.uu.net (Peter da Silva) > Date: 7 Aug 89 13:36:29 GMT > Organization: Xenix Support, FICC > > In article <26998@agate.BERKELEY.EDU>, mwm@eris.berkeley.edu (Mike (I'll think of something yet) Meyer) writes: > > #define errval(x) (errno = 0, (x), errno) > > This is how you get programs that spit out messages like: > > "peter@ficc.uu.net: Not a tty" > IMHO, the error message quoted is due to sloppy programming rather than an error-return mechanism. Some routine returned an error, it's just been mis-interpreted. Mind you, it's not *that* wrong either. You're *not* a tty are you Peter? :-) -----------------------------------------------+------------------------------ Steve Hosgood BSc, | Phone (+44) 792 295213 Image Processing and Systems Engineer, | Fax (+44) 792 295532 Institute for Industrial Information Techology,| Telex 48149 Innovation Centre, University of Wales, | JANET: iiitsh@uk.ac.swan.pyr Swansea SA2 8PP | UUCP: ..!ukc!cybaswan!iiitsh -----------------------------------------------+------------------------------ My views are not necessarily those of my employers! Please note the change in my username as of 1 Aug '89
henry@utzoo.uucp (Henry Spencer) (08/11/89)
In article <601@cybaswan.UUCP> iiitsh@cybaswan.UUCP (Steve Hosgood) writes: >> Interested parties, note: the idea is *guaranteed* to go nowhere unless >> you are interested enough to implement it in a compiler. > >..yeah, but if you implement such a concept in a compiler, you've just put >an extension into it, and that would start to undo all the standards effort >straight away. I hate 'extended' languages - DEC and HP are my least favorite >language vendors for this very reason. It's all a bit 'chicken and egg' if >ANSI won't consider it until someone implements it. It is a sad fact that experimenting with extensions means experimenting with a non-standard language. You have to be convinced that it's worth it. (I personally don't see this as entirely a bad thing -- it cuts down on the number of frivolous experimental extensions. Note, "cuts down", as opposed to "eliminates".) But sane standards committees will indeed refuse to have anything to do with an idea if it has not been tried in an implementation. Language design is **MUCH** harder than it looks; the *only* way to be sure that some wonderful new feature does not interact unpleasantly with existing ones (and that it really is practical and useful) is to implement it and use it in real programming. (Note, not all standards committees are sane. X3J11 did pretty well, on the whole; they only had occasional moments of insanity. You can pretty much tell which moments those were, because the resulting features caught orders of magnitude more flak from the customers.) -- V7 /bin/mail source: 554 lines.| Henry Spencer at U of Toronto Zoology 1989 X.400 specs: 2200+ pages. | uunet!attcan!utzoo!henry henry@zoo.toronto.edu
david@psitech.UUCP (david Fridley) (08/12/89)
I have a new idea, or at least half of one: func(..) { : : if(err) return("func: there has been an error\n"); else return(cptr); } main() { tmp=func(..); if(tmp>_CODESEGMENTSTART && tmp <=CODESEGMENTEND) { /* there has been an error */ } } Advantages: you do not need a global list of error code to figure out what the error is. New functions and libraries can implement their own errors with out fear of confusing meaning with those of other functions/libraries. The pointers will be valid, yet it will be possible to determine that they are errors.. It may even be possible to put error messages in their own seperate sections. Disadvantages: Some compilers may put strings in the data segment, or not even have segments? Some functions may correctly return static strings or pointers to functions. For these functions we won't be able to use this method of error handeling. The basic idea here is to let each module define it's own errors, to avoid global variables (like errno), and to return an otherwise valid pointer that can be determined to be an error with out specific knolege of the errors returned by that function. Standard changes: (The chicken and the egg story). The reason that we have a C standard is so that we can write code that is portable between C compilers. I can not write code that takes advantage of one Company's extensions because it will not run on the other compilers I use (The above Idea will work on all the compilers I use now, but remember it is only half an Idea.). Perhaps after ANSI is finally final (I had to say it (why aren't nested ()'s allowed in English. Where is the English standard committe so I can complain.)) they will be able to consider additions of their own, because this will become the only way to make changes to the language. Perhaps the partisipation of some number of complier companys will be required in order to demonstrate it's fiesability, usefullness, and desirability. If we are going to make additions to C I propose that we make them as general as possible (like returning multiple values from a function), rather than specific (like returning one more value, or an error flag). (ret1,ret2...)=func(p1,p2...) {ret1,ret2,..}=func(p1,p2...) The first one looks better to me than the second, but I am concerned about function, not syntax. -- david. DISCLAIMER: If it's important have a backup. If it ain't broke don't fix it. Proceed at your own risk. My oponions are MY own. Spelling does not count. My fondest dream is to leave this planet.