bobmon@iuvax.cs.indiana.edu (RAMontante) (08/20/88)
Craig Dawson asks about a program in which two routines try to call a third, somewhat as follows: x() { static z(); z(); } y() { static z(); z(); } static z() { ; } (MSC apparently chokes; BTW, TurboC accepts it.) My question is... Why declare z() inside the functions x() and y()? It doesn't make sense that the name "z" should be localized to these code blocks, since it has to be global to the entire file (at least) anyway. Nor do I see the value of making it a static name, since it references an object that can't go away or be "reclaimed" outside of x() or y(), namely a function. Craig's "fix", declaring static z() prior to and outside of both x() and y() (an almost-protoype kind of declaration), seems like the only natural thing to do. Note: I understand why local variables are good. But it seems pointless to treat the function name as "local", since it must refer to a nonlocal object. What am I missing? Is there a relevant section of K&R I should read? -- -- bob,mon (bobmon@iuvax.cs.indiana.edu) -- "Aristotle was not Belgian..." - Wanda
chris@mimsy.UUCP (Chris Torek) (08/21/88)
In article <11879@iuvax.cs.indiana.edu> bobmon@iuvax.cs.indiana.edu (RAMontante) writes: >... somewhat as follows: >x() { static z(); z(); } >y() { static z(); z(); } >static z() { ; } > >(MSC apparently chokes; BTW, TurboC accepts it.) My question is... Why >declare z() inside the functions x() and y()? ... declaring static z() >prior to and outside of both x() and y() ... seems like the only natural >thing to do. Why do some people like a certain 181-novel 1930s and 1940s SF pulp series? The only answer is `style': Some people just do. (Incidentally, with the publication of `In Hell, Madonna' as `The Red Spider', now there are 182.) (Now I wonder how many people will recognise the series named above...) -- In-Real-Life: Chris Torek, Univ of MD Comp Sci Dept (+1 301 454 7163) Domain: chris@mimsy.umd.edu Path: uunet!mimsy!chris
jfh@rpp386.UUCP (The Beach Bum) (08/22/88)
In article <11879@iuvax.cs.indiana.edu> bobmon@iuvax.UUCP (RAMontante) writes: >Craig Dawson asks about a program in which two routines try to call a >third, somewhat as follows: > >x() { static z(); z(); } >y() { static z(); z(); } > >static z() { ; } > >(MSC apparently chokes; BTW, TurboC accepts it.) My question is... Why >declare z() inside the functions x() and y()? It doesn't make sense >that the name "z" should be localized to these code blocks, since it >has to be global to the entire file (at least) anyway. Nor do I see >the value of making it a static name, since it references an object >that can't go away or be "reclaimed" outside of x() or y(), namely a >function. Craig's "fix", declaring static z() prior to and outside of >both x() and y() (an almost-protoype kind of declaration), seems like >the only natural thing to do. the msc compiler is broken. the code should compile without error as written (more or less ...) as for the Rational behind why this is being done, ask the programmer. the minimalist coding would be static z(); x() { z(); } y() { z(); } static z() { ; } a possible rationality behind his coding in the fashion he did is that the functions were actually much larger than what we have above and he wanted to indicate that the functions x() and y() were both dependent on z(). as for why z() is declared to be static, any number of reasons exist. -- John F. Haugh II +--------- Cute Chocolate Quote --------- HASA, "S" Division | "USENET should not be confused with UUCP: killer!rpp386!jfh | something that matters, like CHOCOLATE" DOMAIN: jfh@rpp386.uucp | -- apologizes to Dennis O'Connor
suitti@haddock.ima.isc.com (Steve Uitti) (08/22/88)
In article <5680@rpp386.UUCP> jfh@rpp386.UUCP (The Beach Bum) writes: >In article <11879@iuvax.cs.indiana.edu> bobmon@iuvax.UUCP (RAMontante) writes: >>Craig Dawson asks about a program in which two routines try to call a >>third, somewhat as follows: >> >>x() { static z(); z(); } >>y() { static z(); z(); } >> >>static z() { ; } >> >>(MSC apparently chokes; BTW, TurboC accepts it.) My question is... Why >>declare z() inside the functions x() and y()? Supporting other peoples code is more difficult than supporting your own. A thirty file program where everything (that can be) is declared static is much easier to support than one that doesn't. "ctags", "grep", and cxref only do so much for you. The tighter the scope of each variable and function, the better. I generally try to declare the functions before all uses: static z(a) int a; { ; } static y() { z(5); } static x() { y(); z(); } main() { x(); } Kind of reminds you of Pascal (except that you can tell where "main" starts). The complexity of a program at any point seems to be tied exponentialy to the number of variables and functions available to it at that point. Unfortunately, the compilers that I've used that support prototypes don't "automatically generate" them using this style. If I want prototypes for the above, I need: static z(a) int a; { ; } #ifdef PROTOTYPES_SUPPORTED static z(int a); /* prototype for z() */ #endif /* PROTOTYPES_SUPPORTED */ static y() { z(5); } static x() { y(); z(); } main() { x(); } Which is too bad, since it really has all the info it could possibly want, and I'll probably just screw up the prototype (since I can). On PDP-11's, the linker (ld) can run out of symbol space for the symbol table if you don't do this. Generally, the larger editors that have been ported to this machine got hundreds of routines declared "static", just to allow compilation. This wasn't "bad". It made the products easier to maintain. Another favorite is this: y() { z(); } static z() { ; } This often yields something like "redeclaration of z". The first reference defaults to something like "extern int z();" for a declaration. I've always thought that this was a language feature. It encourages better behaviour without requiring it. Of course the following is fine: static z() { ; } y() { z(); } Stephen
scjones@sdrc.UUCP (Larry Jones) (08/23/88)
In article <5680@rpp386.UUCP>, jfh@rpp386.UUCP (The Beach Bum) writes: > In article <11879@iuvax.cs.indiana.edu> bobmon@iuvax.UUCP (RAMontante) writes: > >Craig Dawson asks about a program in which two routines try to call a > >third, somewhat as follows: > > > >x() { static z(); z(); } > >y() { static z(); z(); } > > > >static z() { ; } > > > >(MSC apparently chokes; BTW, TurboC accepts it.) > > the msc compiler is broken. the code should compile without error > as written (more or less ...) NO!!! Amazingly enough, MSC got this right - the code is wrong. Think about this similar code: x() { static z[]; z[0] = 3; } y() { static z[]; z[0] = 5; } static z[10]; You wouldn't expect that to work, would you? If something is declared within a block, it must be defined within the same block unless it is declared extern. Since you can't define functions within a block, you can't declare a static function within a block. Sorry. ---- Larry Jones UUCP: uunet!sdrc!scjones SDRC scjones@sdrc 2000 Eastman Dr. BIX: ltl Milford, OH 45150 AT&T: (513) 576-2070 Nancy Reagan on superconductivity: "Just say mho."
markro@microsoft.UUCP (Mark Roberts) (08/25/88)
In article <356@sdrc.UUCP> scjones@sdrc.UUCP (Larry Jones) writes: >NO!!! Amazingly enough, MSC got this right - the code is wrong. Thanks for the answer; here is (I believe) the appropriate section from the May 88 draft standard (3.5.1, pg 56, lines 19-20): "The declaration of an identifier for a function that has block scope shall have no explicit storage-class specifier other than extern." [ Amazingly? (:-) ]
haugj@pigs.UUCP (Joe Bob Willie) (08/25/88)
In article <1757@microsoft.UUCP> microsof!markro writes: >In article <356@sdrc.UUCP> scjones@sdrc.UUCP (Larry Jones) writes: >>NO!!! Amazingly enough, MSC got this right - the code is wrong. > >Thanks for the answer; here is (I believe) the appropriate section from the >May 88 draft standard (3.5.1, pg 56, lines 19-20): > > "The declaration of an identifier for a function that has block scope > shall have no explicit storage-class specifier other than extern." is it too late to get this changed back in the standard? this seems to be a serious mis-feature. i have used function declarations inside of functions to document where a function is used. now they are telling us we can't document static functions in this fashion. i know this has been discussed before, but what exactly is The Committee trying to do to C? this one change will result in virtually all of the code i've written being broken. [ along with much code i've not written but still have to maintain ] the resulting language will share only the name with the original language. -- jfh@rpp386.uucp (The Beach Bum at The Big "D" Home for Wayward Hackers) "ANSI C: Just say no" -- Me.
bill@proxftl.UUCP (T. William Wells) (08/26/88)
A random point on prototypes: we have the need to include prototypes in our code while still being able to compile the code with compilers that did not support prototypes. The solution is this: first, all function arguments are of a type for which the argument widening action is null. (ints are OK, short is not.) Second, we have, in a global include file, something like this: /* Configuration section */ #define ANSI_PROTO /* This line would be added if the compiler has prototypes. Note that just using __STDC__ is not sufficient, as there are many compilers that have prototypes but do not define it. */ /* This stuff is buried somewhere deep in the include file, the person compiling our code does not look at it. */ #ifdef ANSI_PROTO #define FUNC(n,p) n p; #else #define FUNC(n,p) n (); #endif This is the code that makes use of the prototype macro. #include <our_file.h> FUNC(int function, (int arg1, int arg2)) What happens is that, in the default file we ship, ANSI_PROTO is not specified and the FUNC macro will expand into something like extern int function(); And, since we use the right argument types, this will work on non-ANSI or ANSI compilers. If, however, the user *does* define ANSI_PROTO, the FUNC macro expands to extern int function(int arg1, int arg2)); and he gets the type checking benefits of the prototype. --- Bill novavax!proxftl!bill
iiit-sh@cybaswan.UUCP (Steve Hosgood) (08/31/88)
In article <1757@microsoft.UUCP> microsof!markro writes: >..... here is (I believe) the appropriate section from the >May 88 draft standard (3.5.1, pg 56, lines 19-20): > > "The declaration of an identifier for a function that has block scope > shall have no explicit storage-class specifier other than extern." In article <371@pigs.UUCP> haugj@pigs.UUCP (Joe Bob Willie) writes: >is it too late to get this changed back in the standard? this seems to >be a serious mis-feature. i have used function declarations inside >of functions to document where a function is used. now they are telling >us we can't document static functions in this fashion. > >i know this has been discussed before, but what exactly is The Committee >trying to do to C? this one change will result in virtually all of the >code i've written being broken. [ along with much code i've not written >but still have to maintain ] the resulting language will share only the >name with the original language. I agree, Joe Bob, I've got the same problem exactly! This had better get to the the comp.std.c group *now* so they can discuss it before it *is* too late. I think the compiler is correct according to the standard, but the standard is broken. However, the compiler *ought* to produce an error message. After all, declaring a function static within a block would mean that it would have to be *defined* within that block in order to be both visible and usable. However, C has no mechanism for declaring functions within blocks, so at very least the static declaration should cause an error message to that effect. Someone's pinched my K&R, but I'm sure it says that this is a special case for the reasons I've mentioned above. ANSI have *got* to decide one way or another, I hope they change lines 19-20, page 56! I hope no-one objects, but I've directed follow-ups to comp.std.c Even if ANSI are right, I think you'd agree that this is a standards problem now, not just MSC. -----------------------------------------------+------------------------------ 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: iiit-sh@uk.ac.swan.pyr Swansea SA2 8PP | UUCP: ..!ukc!cybaswan.UUCP!iiit-sh ----------------------------------------+------------------------------------- My views are not necessarily those of my employers!
mouse@mcgill-vision.UUCP (der Mouse) (09/01/88)
In article <371@pigs.UUCP>, haugj@pigs.UUCP (Joe Bob Willie) writes: > In article <1757@microsoft.UUCP> microsof!markro writes: >> In article <356@sdrc.UUCP> scjones@sdrc.UUCP (Larry Jones) writes: >>> NO!!! Amazingly enough, MSC got this right - the code is wrong. >> [F]rom the May 88 draft standard (3.5.1, pg 56, lines 19-20): >> "The declaration of an identifier for a function that has block >> scope shall have no explicit storage-class specifier other than >> extern." > i have used function declarations inside of functions to document > where a function is used. now they are telling us we can't document > static functions in this fashion. Not at all; just that you can't mention that they're static in the block. I *would* be surprised to find that there's anything wrong with something like foo() { ... { double glurf(char*,int); ... } ... } static double glurf(char *s,int maxlen) { ... } You're confusing the two meanings of the static keyword. When used inside a function, `static' means one thing: the object being declared has static storage class. Here, `static' really is a storage class specifier. Outside a function, `static' means something else: the name being declared is to be accessible only from within the file the definition appears in. Here, it's really a linkage specifier rather than a storage class specifier. In retrospect, I think it was probably a mistake to overload `static' this way, but it is certainly far too late to change it now. der Mouse old: mcgill-vision!mouse new: mouse@larry.mcrcim.mcgill.edu
chris@mimsy.UUCP (Chris Torek) (09/01/88)
In article <1275@mcgill-vision.UUCP> mouse@mcgill-vision.UUCP (der Mouse) writes: >... I *would* be surprised to find that there's anything wrong with >something like [compressed vertically] >foo() { ... { double glurf(char*,int); ... } } >static double glurf(char *s,int maxlen) { ... } Surprise! According to the dpANS, the first declaration of a static function must label that function as static. Now we also know (from the discussion chain in the references: line) that function declarations within other functions may not be labelled `static'. Putting these together, the *only* legal ways to write this are: static double glurf(char *, int); foo() { ... /* call glurf */ ... } static double glurf(char *s, int maxlen) { ... } or static double glurf(char *s, int maxlen) { ... } foo() { ... /* call glurf */ ... } -- In-Real-Life: Chris Torek, Univ of MD Comp Sci Dept (+1 301 454 7163) Domain: chris@mimsy.umd.edu Path: uunet!mimsy!chris
bill@proxftl.UUCP (T. William Wells) (09/03/88)
In article <13344@mimsy.UUCP> chris@mimsy.UUCP (Chris Torek) writes:
: Surprise!
:
: According to the dpANS, the first declaration of a static function must
: label that function as static. Now we also know (from the discussion
: chain in the references: line) that function declarations within other
: functions may not be labelled `static'. Putting these together, the
: *only* legal ways to write this are:
:
: static double glurf(char *, int);
: foo() { ... /* call glurf */ ... }
: static double glurf(char *s, int maxlen) { ... }
:
: or
:
: static double glurf(char *s, int maxlen) { ... }
: foo() { ... /* call glurf */ ... }
Yes. Shriek! Scream! Shout! Curse! Puke! etc.................................
All in the name of easing a few implementers' lives.
Shame on you X3J11.
---
To change the subject slightly: a new hire was asking me if he
could use some macros to encapsulate some flag setting.
I told him no.
Why?
Because the only purpose of the macro was to decrease the number
of keystrokes *he* had to use. But it would have made the next
reader of the code have to understand two different things, the
macro AND the flag, to understand the code, instead of one.
He asked me why. I said: this code will be written once and read
many hundred times. Whose job do you think ought to be made
easier: yours or that future reader (who may be yourself, several
times)? He got the point.
How is this relevant, you might ask?
Well, consider the related question: who should have to deal with
the pain caused by systems that make one pass compilation
difficult: every user of ANSI C, or those people charged with the
writing of a C compiler for those systems?
It seems that the committee forgot this.
For shame!
(And yes, even though I think the committee has done a generally
good job, I will take every opportunity to condemn them for this
egregious lapse.)
---
Bill
novavax!proxftl!bill
james@bigtex.uucp (James Van Artsdalen) (09/05/88)
In article <697@proxftl.UUCP>, bill@proxftl.UUCP (T. William Wells) wrote: > All in the name of easing a few implementers' lives. > Shame on you X3J11. > [...] who should have to deal with the pain caused by systems that > make one pass compilation difficult: every user of ANSI C, or those > people charged with the writing of a C compiler for those systems? It's worse than all that. ANSI C permits conflicting function declarations without a warning - indeed it is required that no warning be given. For example, consider the following in the context of a far memory model on the 286: int a() { int b(); return b(); } char * b() { return "foo"; } A purely ANSI C compiler must not generate an error according to ANSI C, because the incorrect declaration of b() is hidden within the scope of a(). Yet this program cannot work, and I can't conceive of any implementation where the ANSI C requirement is actually useful. The nature of functions in C is such that the *definitions* cannot be scoped (ie, you can't place a function definition within the scope of another function as you can in Pascal): it is not clear why it is desirable that function *declarations* should be subject to scoping. I too think that the ANSI C committee did a very good job overall. -- James R. Van Artsdalen ...!uunet!utastro!bigtex!james "Live Free or Die" Home: 512-346-2444 Work: 328-0282; 110 Wild Basin Rd. Ste #230, Austin TX 78746
tif@cpe.UUCP (09/06/88)
Written 6:40 pm Sep 4, 1988 by bigtex.UUCP!james in cpe:comp.sy.ibm.pc >It's worse than all that. ANSI C permits conflicting function >declarations without a warning - indeed it is required that no warning >be given. ... >... and I can't conceive of any >implementation where the ANSI C requirement is actually useful. I can. When you want to use a return value in more than one way. a() { int *malloc(), *x; x = malloc(sizeof(int)); } b() { long *malloc(), *x; x = malloc(sizeof(long)); } Paul Chamberlain Computer Product Engineering, Tandy Corp. {convex,killer}!ninja!cpe!tif
haugj@pigs.UUCP (The Beach Bum) (09/09/88)
In article <12400016@cpe> tif@cpe.UUCP writes: >Written 6:40 pm Sep 4, 1988 by bigtex.UUCP!james in cpe:comp.sy.ibm.pc >>It's worse than all that. ANSI C permits conflicting function >>declarations without a warning - indeed it is required that no warning >>be given. ... >>... and I can't conceive of any >>implementation where the ANSI C requirement is actually useful. > >I can. When you want to use a return value in more than one way. bad move. if the return value is actually (char *), declaring the function to return (long *) is NOT going to have the same effect as an explicit cast in all situations. various C compilers return pointers in one register and non-pointers in another. the system v/68k compiler from motorola comes to mind as one which has behavior like this. other machines have different formats for pointers to different objects. the CORRECT, PORTABLE, method is to correctly declare the return value and then cast the result. -- =-=-=-=-=-=-=-The Beach Bum at The Big "D" Home for Wayward Hackers-=-=-=-=-=-= Very Long Address: John.F.Haugh@rpp386.dallas.tx.us Very Short Address: jfh@rpp386 "ANSI C: Just say no" -- Me
mouse@mcgill-vision.UUCP (der Mouse) (09/11/88)
In article <13344@mimsy.UUCP>, chris@mimsy.UUCP (Chris Torek) writes: > In article <1275@mcgill-vision.UUCP> mouse@mcgill-vision.UUCP (der Mouse) writes: >> I *would* be surprised to find that [this doesn't work] >> foo() { ... { double glurf(char*,int); ... } } >> static double glurf(char *s,int maxlen) { ... } > Surprise! You have such a lovely way of phrasing things, Chris... :-) > Putting these together, the *only* legal ways to write this are: > static double glurf(char *, int); > foo() { ... /* call glurf */ ... } > static double glurf(char *s, int maxlen) { ... } > or > static double glurf(char *s, int maxlen) { ... } > foo() { ... /* call glurf */ ... } Since the whole idea was to document the fact that foo calls glurf, near the point of call (ie, in foo), how about: static double glurf(char *, int); foo() { double glurf(char *, int); ... /* call glurf */ ... } static double glurf(char *s, int maxlen) { ... } Is this permitted? der Mouse old: mcgill-vision!mouse new: mouse@larry.mcrcim.mcgill.edu
james@bigtex.uucp (James Van Artsdalen) (09/12/88)
In article <12400016@cpe>, tif@cpe.UUCP wrote: | I can. When you want to use a return value in more than one way. | a() { | int *malloc(), *x; | x = malloc(sizeof(int)); | } | | b() { | long *malloc(), *x; | x = malloc(sizeof(long)); | } This won't work right: it's not at all portable. It assumes that sizeof(int *) == sizeof(long*), an assumption which isn't always true. -- James R. Van Artsdalen ...!uunet!utastro!bigtex!james "Live Free or Die" Home: 512-346-2444 Work: 328-0282; 110 Wild Basin Rd. Ste #230, Austin TX 78746
gordon@sneaky.TANDY.COM (Gordon Burditt) (09/12/88)
In article <12400016@cpe>, tif@cpe.UUCP writes: > Written 6:40 pm Sep 4, 1988 by bigtex.UUCP!james in cpe:comp.sy.ibm.pc > >It's worse than all that. ANSI C permits conflicting function > >declarations without a warning - indeed it is required that no warning > >be given. ... Error: a diagnostic message that indicates that the program is non-conforming. Error messages are required by the standard under appropriate circumstances. Examples: "syntax error, line 127", "undeclared variable 'foo', line 64", and "include file 'foo.h' cannot be opened". Normally an error prohibits linking and execution of the program. Warning: a diagnostic message that does not indicate that the program is non-conforming. The presence of a warning must not prohibit the program from being run. ANSI C does not anywhere prohibit warnings for any idiotic or non-idiotic reason whatsoever: Warning - source program contains the character 'm'. Warning - use of single-character variable names - docking your paycheck $50.00 Warning - statement not reached Warning - source program contains the character 'a'. Compilation complete, 0 errors, 1 warnings, job cost $8.37 Warning - obscene variable name - naughty, naughty. Warning - implicit conversion from long to int may lose precision. Gag, barf, bletch - trigraphs used. Ick! Warning - indentation style does not match braces. Warning - numeric constant 3.14 is an inaccurate approximation for pi. Warning - division by three. Warning - numeric constant used - using a #define is preferred style. Warning - supplied MasterCard number is within $10.00 of credit limit. Warning - spelling error in comment. Warning - no warnings generated Warning - comments do not match code Warning - non-K&R I indentation style used Some existing compilers produce single-character warnings on every character in the code, paginated and with line numbers. This is sometimes referred to as a "compiler listing". > >... and I can't conceive of any > >implementation where the ANSI C requirement is actually useful. > I can. When you want to use a return value in more than one way. > a() { > int *malloc(), *x; > x = malloc(sizeof(int)); > } > > b() { > long *malloc(), *x; > x = malloc(sizeof(long)); > } At least one of these calls is likely to return garbage. Besides the problem that there is no guarantee that int * and long * have the same size, format, byte ordering, or bit ordering, every sane (read: how I would write it if my supply of drugs holds out :-) ) *86 compiler returns a (far) char * in ES:AX, and a (far) long * in ES:DX. Naturally, (far) unsigned char * is returned in AX:DX, and (far) unsigned long * in DX:AX. (far) int * is returned in BX:AX and short * is returned in CX:DX (Yes, even if short and int are the same size!) I think mismatched declarations like this ought to be a "common warning", even if it isn't an error. Regardless of what you think of the above linkage conventions, the implementer is still permitted to do this. Taking a more real example, on some 68000 implementations, pointers are returned in a0 and integers (of various sizes) are returned in d0. Since Berkeley and USG systems disagree over whether sprintf() returns the (char *) buffer given in the first argument or the (int) number of characters written in the buffer, someone wrote an assembly-language version of sprintf() that returned both values. Assuming that all programs that use the return value declare it correctly (dream on!), they could all get the expected return value. Cute, but unportable in the extreme! Another possibility for 8086 systems (which DO NOT have a protected mode!): Require that all structures and unions line up on a 16-byte boundary. Now, make a far struct pointer *16 BITS* - what you would load into the segment register to access it with an offset of 0. This is, of course, very different from the 16-bit near pointer, even if it is the same size. Pointers to ints, chars, etc. would still require at least a 24-bit (and probably 32-bit, for convenience of representation) far pointer. You could save some code making references like structptr->foo this way. Since it isn't upward-compatible to protected mode, compiler-writers aren't likely to do this. Gordon L. Burditt ...killer!ninja!sneaky!gordon
iiit-sh@cybaswan.UUCP (Steve Hosgood) (09/13/88)
In article <12400016@cpe> tif@cpe.UUCP writes: >bigtex.UUCP!james in cpe:comp.sy.ibm.pc writes: >>It's worse than all that. ANSI C permits conflicting function >>declarations without a warning - indeed it is required that no warning >>be given. ... >>... and I can't conceive of any >>implementation where the ANSI C requirement is actually useful. > >I can. When you want to use a return value in more than one way. [ example deleted ] Yeah, but surely the *storage class* of the function declaration shouldn't be allowed to conflict? The example showed good use of conflicting *types*, can anyone justify having the same name declared 'static' and 'extern' in the same file? I can't. -----------------------------------------------+------------------------------ 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: iiit-sh@uk.ac.swan.pyr Swansea SA2 8PP | UUCP: ..!ukc!cybaswan.UUCP!iiit-sh ----------------------------------------+------------------------------------- My views are not necessarily those of my employers!
gary@apexepa.UUCP (Gary Wisniewski) (09/13/88)
In article <12400016@cpe> tif@cpe.UUCP writes: > >Written 6:40 pm Sep 4, 1988 by bigtex.UUCP!james in cpe:comp.sy.ibm.pc >>It's worse than all that. ANSI C permits conflicting function >>declarations without a warning - indeed it is required that no warning >>... and I can't conceive of any >>implementation where the ANSI C requirement is actually useful. > >I can. When you want to use a return value in more than one way. > >a() { > int *malloc(), *x; > x = malloc(sizeof(int)); >} > >b() { > long *malloc(), *x; > x = malloc(sizeof(long)); >} You can get away with this, but donn your asbestos suit if you say this in comp.lang.c! This won't work for machines which have different pointer formats for different data types. char *malloc(); long *x; x = (long *) malloc(sizeof(long)); The above tells the compiler that it needs to explicitly coerce a char* to a long*. Your code above just assumes that malloc returns a long*; not valid on many machines (Data General, for instance). -- Gary J. Wisniewski Apex Software Corporation {allegra,bellcore,cadre}!pitt!darth!apexepa!gary Phone: (412) 681-4343