int func() v/s int func(void)

Discussion in 'C Programming' started by Vinko Vrsalovic, Jan 21, 2005.

  1. Hello,

    I read a couple of posts ago that these are not equivalent, and that
    the former means 'no arguments specified' and that calling for
    instance func(3,"THREE",&myint) is legal.

    What's the intended use of that way of declaring functions?

    Thanks,
    V.
    Vinko Vrsalovic, Jan 21, 2005
    #1
    1. Advertising

  2. Vinko Vrsalovic

    Mike Wahler Guest

    "Vinko Vrsalovic" <> wrote in message
    news:...

    > Re: int func() v/s int func(void)


    (If the text of your subject is intended as part of
    your message, put it in your message. Not everyone's
    newsreader shows the subject and body simultaneously,
    in which case context is lost.)

    > Hello,
    >
    > I read a couple of posts ago that these are not equivalent,


    Correct.

    >and that
    > the former means 'no arguments specified'


    Correct. (void) means specifically 'no arguments'.

    >and that calling for
    > instance func(3,"THREE",&myint) is legal.


    It's 'legal' but might not 'work' (could produce undefined
    behavior if not used correctly -- i.e. the function must
    be written to handle those arguments).

    > What's the intended use of that way of declaring functions?


    To write fragile code. IOW Don't Do That. It's an
    anachronism from the days before prototypes were
    added to C. (It's been kept so that old code will
    still compile). Prototypes help you create correct
    code, by enabling the compiler to do better error
    checking. Use them. Always.


    -Mike
    Mike Wahler, Jan 21, 2005
    #2
    1. Advertising

  3. Vinko Vrsalovic

    -berlin.de Guest

    Vinko Vrsalovic <> wrote:

    Please put what you're talking about into the body of your mail,
    subject lines get ofter truncated by the news reader, making what
    you ask about hard or even impossible to understand...

    Subject: int func() v/s int func(void)

    > I read a couple of posts ago that these are not equivalent, and that
    > the former means 'no arguments specified' and that calling for
    > instance func(3,"THREE",&myint) is legal.


    > What's the intended use of that way of declaring functions?


    It keeps the compiler from checking if you use the function with a well-
    defined number of arguments and types. One "intended" use I can think of
    is for pre-ANSI programs (written before about 1989) were you didn't had
    function prototypes but which you still want modern compilers to be able
    to compile. Another possible use is for declaration of function pointers
    in plug-in systems where the number of arguments isn't known at compile
    time but where e.g. libraries can be loaded while the program is already
    running and you have methods to determine how many (or which) arguments
    that function accepts (and then call the function accordingly). E.g. you
    may have (non-standard and probably system-specific) functions called
    pointer_to_func() and required_arg_count() to be used like this

    int ( *to_be_loded )( ); /* arguments unspecified ! */
    int num_args;
    int result;

    to_be_loaded = pointer_to_func( "name_of_function_to_be_loaded" );
    num_args = required_arg_count( "name_of_function_to_be_loaded" );

    if ( num_args == 0 )
    result = to_be_loaded();
    else if ( num_args == 1 )
    result = to_be_loaded( 42 );
    else
    {
    fprintf( stderr, "Too many arguments required\n" );
    exit( EXIT_FAILURE );
    }
    Regards, Jens
    --
    \ Jens Thoms Toerring ___ -berlin.de
    \__________________________ http://www.toerring.de
    -berlin.de, Jan 21, 2005
    #3
  4. Vinko Vrsalovic

    Eric Sosman Guest

    Vinko Vrsalovic wrote:

    > Hello,
    >
    > I read a couple of posts ago that these are not equivalent, and that
    > the former means 'no arguments specified' and that calling for
    > instance func(3,"THREE",&myint) is legal.
    >
    > What's the intended use of that way of declaring functions?


    It's a leftover from the early development of C,
    retained so code written prior to the creation of the
    ANSI Standard had a hope of continuing to work correctly.

    Old-time ("K&R") C had no function prototypes; all you
    could say about a function defined "elsewhere" is that it
    returned such-and-such a type. You could not describe the
    number and types of the arguments except in the actual
    function definition, which you did like this:

    int func(a, b, c)
    int a;
    char *b;
    int *c;
    {
    /* do stuff */
    return 42;
    }

    .... and in some other module you'd declare it as

    int func();
    or
    extern int func();

    .... so no information about the arguments was given in the
    declaration.

    ANSI C swiped an idea from C++ to allow much more detailed
    specification of functions; the idea was a good one, and all
    new (i.e., for the last ten or twelve years) should use the
    newer form. Still, the old form is kept around in the name of
    backwards compatibility. (A name not to be trifled with, I might
    add: C has been Standard-ized for less than half its life, and
    quite a lot of code from its adolescent years is still around.)

    --
    Eric Sosman
    lid
    Eric Sosman, Jan 21, 2005
    #4
  5. Vinko Vrsalovic

    sushant Guest

    in the declaration int func( ) means that u can pass any type and
    number of arguments in the function func() which has the return type
    int . but the declaration int func(void) means that u dont have to pass
    any arguments in that function . this is the way C89 works but in C99
    the former declartion and latter both are same ...
    Vinko Vrsalovic wrote:
    > Hello,
    >
    > I read a couple of posts ago that these are not equivalent, and that
    > the former means 'no arguments specified' and that calling for
    > instance func(3,"THREE",&myint) is legal.
    >
    > What's the intended use of that way of declaring functions?
    >
    > Thanks,
    > V.
    sushant, Jan 21, 2005
    #5
  6. Vinko Vrsalovic wrote:
    > Hello,
    >
    > I read a couple of posts ago that these are not equivalent, and that
    > the former means 'no arguments specified' and that calling for
    > instance func(3,"THREE",&myint) is legal.
    >
    > What's the intended use of that way of declaring functions?
    >
    > Thanks,
    > V.


    Use ``int foo(void)" in your header files when you want to tell
    the compiler explicitly that this function *does not* take any
    arguments. ``int foo()" would allow it to use any number
    of arguments. A good compiler would also warn you about this
    (Intel's compiler does).

    Regards,
    Jonathan.

    --
    "I'm learning to program because then I can write
    programs to do my homework faster." - Andy Anfilofieff
    Jonathan Burd, Jan 21, 2005
    #6
  7. Vinko Vrsalovic

    Villy Kruse Guest

    On Thu, 20 Jan 2005 20:36:26 -0500,
    Eric Sosman <> wrote:



    In GNU and other open source for unix you often see something like:


    #if USE_ANSI_PROTOTYPE
    int func (int a, int b);
    #else
    int func ();
    #endif

    int func (a, b)
    int a;
    int b;
    {
    ...
    }

    The conditional compilation of the prototype can easily be implelemted
    using a macro, so it doesn't look to desturbing visualy. It took a very
    long time before all C compilers on unix systems were ANSI capable,
    especialy for systems where the manufacturer stopped upgrading their
    unix implementations. I beleive that most C compilers for MS-DOS were
    ANSI or mostly ANSI from the beginning.

    >
    > ANSI C swiped an idea from C++ to allow much more detailed
    > specification of functions; the idea was a good one, and all
    > new (i.e., for the last ten or twelve years) should use the
    > newer form. Still, the old form is kept around in the name of
    > backwards compatibility. (A name not to be trifled with, I might
    > add: C has been Standard-ized for less than half its life, and
    > quite a lot of code from its adolescent years is still around.)
    >


    If I'm not mistaken, in C++ func() means the same as func(void) would
    mean in the C language. C++ at the time didn't have any legacy code to
    consider.


    Villy
    Villy Kruse, Jan 21, 2005
    #7
  8. Vinko Vrsalovic

    Nejat AYDIN Guest

    sushant wrote:
    > Vinko Vrsalovic wrote:
    > > Hello,
    > > I read a couple of posts ago that these are not equivalent, and that
    > > the former means 'no arguments specified' and that calling for
    > > instance func(3,"THREE",&myint) is legal.
    > >
    > > What's the intended use of that way of declaring functions?

    >
    > in the declaration int func( ) means that u can pass any type and
    > number of arguments in the function func() which has the return type
    > int . but the declaration int func(void) means that u dont have to pass
    > any arguments in that function .


    The declaration "int func(void)" means you *cannot* pass any argument
    to that function.

    > this is the way C89 works but in C99
    > the former declartion and latter both are same ...


    No. They are *not* same in C99 either.
    Nejat AYDIN, Jan 21, 2005
    #8
  9. Vinko Vrsalovic

    Eric Sosman Guest

    Villy Kruse wrote:

    > In GNU and other open source for unix you often see something like:
    >
    >
    > #if USE_ANSI_PROTOTYPE
    > int func (int a, int b);
    > #else
    > int func ();
    > #endif
    >
    > int func (a, b)
    > int a;
    > int b;
    > {
    > ...
    > }


    Despite its apparent simplicity, this approach can be
    difficult to use correctly. It's fine if all the arguments
    are `int' (as in your example) or `double' or pointers or
    structs or unions -- but if they're `char' or `unsigned short'
    or `time_t' or ... The problem is that these types may be
    subject to the default argument promotions when passed to a
    K&R function, and you don't know at coding time whether they're
    promotable, nor to what.

    As a concrete example, try writing a prototype for

    enum Cubs { TINKER, EVERS, CHANCE };
    double play(x)
    enum Cubs x;
    {...}

    To write the prototype, you need to discover what type
    an `enum Cubs' argument will promote to. Since the compiler
    can choose any integer type at all to represent `enum Cubs'
    and since the promotion rules for the integer types are, to
    some extent, implementation-dependent (e.g., `unsigned short'
    promotes to `int' on some systems, `unsigned int' on others),
    you find yourself in the uncomfortable position of trying to
    out-guess every compiler that will ever process the code.

    The upshot is that the only declaration for play()
    you can be utterly confident in is

    double play();

    .... which loses, er, "some" of the benefits of prototypes.
    Anything else risks lying to the compiler -- and we all
    know what happens, sooner or later, when you lie to the
    compiler.

    --
    Eric Sosman
    lid
    Eric Sosman, Jan 21, 2005
    #9
  10. Vinko Vrsalovic

    CBFalconer Guest

    Eric Sosman wrote:
    >

    .... snip ...
    >
    > As a concrete example, try writing a prototype for
    >
    > enum Cubs { TINKER, EVERS, CHANCE };
    > double play(x)
    > enum Cubs x;
    > {...}
    >
    > To write the prototype, you need to discover what type
    > an `enum Cubs' argument will promote to. Since the compiler
    > can choose any integer type at all to represent `enum Cubs'
    > and since the promotion rules for the integer types are, to
    > some extent, implementation-dependent (e.g., `unsigned short'
    > promotes to `int' on some systems, `unsigned int' on others),
    > you find yourself in the uncomfortable position of trying to
    > out-guess every compiler that will ever process the code.


    Why? Why can't we just write the prototype as:

    double play(enum Cubs x);
    and then
    double play(enum Cubs x)
    {
    int retval = 0;

    switch (x) {
    case TINKER: snag();
    if (caughtfly) retval++;
    break;
    case EVERS: touchnthrow();
    if (intime2) retval++;
    break;
    case CHANCE: stretchntouch();
    if (intime1) retval++;
    break;
    default: error();
    }
    return retval;
    }

    and I see no need to outguess or lie to the compiler.

    --
    "If you want to post a followup via groups.google.com, don't use
    the broken "Reply" link at the bottom of the article. Click on
    "show options" at the top of the article, then click on the
    "Reply" at the bottom of the article headers." - Keith Thompson
    CBFalconer, Jan 21, 2005
    #10
  11. Jonathan Burd <> writes:
    > Vinko Vrsalovic wrote:
    >> Hello,
    >> I read a couple of posts ago that these are not equivalent, and that
    >> the former means 'no arguments specified' and that calling for
    >> instance func(3,"THREE",&myint) is legal.
    >> What's the intended use of that way of declaring functions?
    >> Thanks,
    >> V.

    >
    > Use ``int foo(void)" in your header files when you want to tell
    > the compiler explicitly that this function *does not* take any
    > arguments. ``int foo()" would allow it to use any number
    > of arguments. A good compiler would also warn you about this
    > (Intel's compiler does).


    In either case, a call must pass the number and types of arguments
    consistent with the definition of foo(). The difference between the
    declarations "int foo(void);" and "int foo();" is that the latter
    doesn't let the compiler diagnose argument errors; it makes a call
    with the wrong number of arguments undefined behavior rather than an
    error requiring a compile-time diagnostic.

    --
    Keith Thompson (The_Other_Keith) <http://www.ghoti.net/~kst>
    San Diego Supercomputer Center <*> <http://users.sdsc.edu/~kst>
    We must do something. This is something. Therefore, we must do this.
    Keith Thompson, Jan 21, 2005
    #11
  12. Vinko Vrsalovic

    Eric Sosman Guest

    CBFalconer wrote:
    > Eric Sosman wrote:
    >
    > ... snip ...
    >
    >> As a concrete example, try writing a prototype for
    >>
    >> enum Cubs { TINKER, EVERS, CHANCE };
    >> double play(x)
    >> enum Cubs x;
    >> {...}
    >>
    >> To write the prototype, you need to discover what type
    >>an `enum Cubs' argument will promote to. Since the compiler
    >>can choose any integer type at all to represent `enum Cubs'
    >>and since the promotion rules for the integer types are, to
    >>some extent, implementation-dependent (e.g., `unsigned short'
    >>promotes to `int' on some systems, `unsigned int' on others),
    >>you find yourself in the uncomfortable position of trying to
    >>out-guess every compiler that will ever process the code.

    >
    >
    > Why? Why can't we just write the prototype as:
    >
    > double play(enum Cubs x);


    For the same reason that the prototype for
    `void func(f) float f; {...}' is not `void func(float)'
    but `void func(double)'.

    --
    Eric Sosman, Jan 21, 2005
    #12
  13. -berlin.de wrote:
    > Vinko Vrsalovic <> wrote:
    >
    > Please put what you're talking about into the body of your mail,
    > subject lines get ofter truncated by the news reader, making what
    > you ask about hard or even impossible to understand...


    Ok, will do. Thanks everyone.

    >[...]
    > to compile. Another possible use is for declaration of function

    pointers
    > in plug-in systems where the number of arguments isn't known at

    compile
    > time but where e.g. libraries can be loaded while the program is

    already
    > running and you have methods to determine how many (or which)

    arguments
    > that function accepts (and then call the function accordingly). E.g.

    you
    > may have (non-standard and probably system-specific) functions called
    > pointer_to_func() and required_arg_count() to be used like this


    But from all the other answers I'd say this is more a side-effect than
    an intended use. Anyhow, an interesting side-effect :)

    Regards,
    V.
    Vinko Vrsalovic, Jan 21, 2005
    #13
  14. Vinko Vrsalovic

    Chris Torek Guest

    >Eric Sosman wrote:
    >... snip ...
    >> As a concrete example, try writing a prototype for
    >> enum Cubs { TINKER, EVERS, CHANCE };
    >> double play(x)
    >> enum Cubs x;
    >> {...}

    [more snippage]

    In article <>
    CBFalconer <> wrote:
    >Why? Why can't we just write the prototype as:
    >
    > double play(enum Cubs x);
    >and then
    > double play(enum Cubs x)
    > {

    [code snipped]

    You can indeed write that. Moreover, you *should* write that, as
    long as your compiler is not three decades old now. :) But you
    have sidestepped the problem that Eric Sosman was describing, which
    is:

    "come up with a way to write a prototype declaration for
    this function defined with an old-style, rather than modern
    prototype-style, definition"

    (which problem in turn comes up when trying to write code that
    compiles with ancient C compilers -- to which the best answer is
    now: "stop using that ancient C compiler". :) )

    Seriously, it used to be important to write C code that could
    compile on pre-1989-Standard C compilers. It also used to be 1991.
    --
    In-Real-Life: Chris Torek, Wind River Systems
    Salt Lake City, UT, USA (40°39.22'N, 111°50.29'W) +1 801 277 2603
    email: forget about it http://web.torek.net/torek/index.html
    Reading email is like searching for food in the garbage, thanks to spammers.
    Chris Torek, Jan 21, 2005
    #14
  15. Vinko Vrsalovic

    Villy Kruse Guest

    On Fri, 21 Jan 2005 08:53:22 -0500,
    Eric Sosman <> wrote:


    >
    > Despite its apparent simplicity, this approach can be
    > difficult to use correctly. It's fine if all the arguments
    > are `int' (as in your example) or `double' or pointers or


    which they also are where this is done in real programs.



    Villy
    Villy Kruse, Jan 24, 2005
    #15
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Ollej Reemt
    Replies:
    7
    Views:
    502
    Jack Klein
    Apr 22, 2005
  2. Stig Brautaset

    `void **' revisited: void *pop(void **root)

    Stig Brautaset, Oct 25, 2003, in forum: C Programming
    Replies:
    15
    Views:
    779
    The Real OS/2 Guy
    Oct 28, 2003
  3. Replies:
    5
    Views:
    817
    S.Tobias
    Jul 22, 2005
  4. Replies:
    1
    Views:
    395
    Victor Bazarov
    May 23, 2007
  5. Barry
    Replies:
    3
    Views:
    318
    Neelesh Bodas
    Jul 31, 2007
Loading...

Share This Page