Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
  1. Home
  2. The Lounge
  3. ( C/C++ historical question) was there a point in time where adding a return at the end of a void function was required ?

( C/C++ historical question) was there a point in time where adding a return at the end of a void function was required ?

Scheduled Pinned Locked Moved The Lounge
questionc++devops
37 Posts 23 Posters 5 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • G Gary Wheeler

    honey the codewitch wrote:

    Interestingly you can call main() from inside your C app, but not in C++.

    Really? I didn't know that. I'll admit it's probably not a good idea, and there are easy ways around the prohibition, ... Hmm. I think I've figured some of it out.

    • There are multiple valid forms of main(...), and implementation-defined arguments are allowed. Allowing calls to it might require too much special case handling between the compiler and linker to ensure a match between the call and the actual implementation.
    • Another factor might be runtime initialization that takes place in main()'s prolog.
    • Objects declared static could potentially call main() before it had been called for the actual application startup. X|

    Sounds like the prohibition is a good way to make the compiler, linker, and runtime initialization job easier.

    Software Zen: delete this;

    H Offline
    H Offline
    honey the codewitch
    wrote on last edited by
    #16

    Part of it might be static initialization behavior in C++ precludes it, but I don't know enough about the machinations of all that to be certain of anything.

    Check out my IoT graphics library here: https://honeythecodewitch.com/gfx And my IoT UI/User Experience library here: https://honeythecodewitch.com/uix

    1 Reply Last reply
    0
    • H honey the codewitch

      I believe it never was, as it was meant to be more or less compatible with C code, which doesn't require it. Interestingly you can call main() from inside your C app, but not in C++.

      Check out my IoT graphics library here: https://honeythecodewitch.com/gfx And my IoT UI/User Experience library here: https://honeythecodewitch.com/uix

      C Offline
      C Offline
      CPallini
      wrote on last edited by
      #17

      This piece of code

      int main()
      {
      main();
      }

      compiles fine. Anyway, I didn't try to run the executable. :laugh:

      "In testa che avete, Signor di Ceprano?" -- Rigoletto

      H 1 Reply Last reply
      0
      • C CPallini

        This piece of code

        int main()
        {
        main();
        }

        compiles fine. Anyway, I didn't try to run the executable. :laugh:

        "In testa che avete, Signor di Ceprano?" -- Rigoletto

        H Offline
        H Offline
        honey the codewitch
        wrote on last edited by
        #18

        Hmm, well I've never actually tried it. I was relying on a lecture on C++. I doubt it's standard though. I'm pretty sure dude knew what he was on about. He wasn't a nobody, but I forget his title.

        Check out my IoT graphics library here: https://honeythecodewitch.com/gfx And my IoT UI/User Experience library here: https://honeythecodewitch.com/uix

        C 1 Reply Last reply
        0
        • M Maximilien

          I see a lot of things like this in the project I'm working on: Was it necessary at some point in time ? Was this an ancient C syntax ?

          void f(){
          // .... do something
          return;
          }

          I would not be surprised if I see old K&R syntax somewhere like this

          void f( a )
          int a
          {
          }

          CI/CD = Continuous Impediment/Continuous Despair

          L Offline
          L Offline
          Lost User
          wrote on last edited by
          #19

          Maybe it's tag that has meaning only to the "creator". Mine are leftovers from extending a function then changing my mind.

          "Before entering on an understanding, I have meditated for a long time, and have foreseen what might happen. It is not genius which reveals to me suddenly, secretly, what I have to say or to do in a circumstance unexpected by other people; it is reflection, it is meditation." - Napoleon I

          1 Reply Last reply
          0
          • H honey the codewitch

            Hmm, well I've never actually tried it. I was relying on a lecture on C++. I doubt it's standard though. I'm pretty sure dude knew what he was on about. He wasn't a nobody, but I forget his title.

            Check out my IoT graphics library here: https://honeythecodewitch.com/gfx And my IoT UI/User Experience library here: https://honeythecodewitch.com/uix

            C Offline
            C Offline
            CPallini
            wrote on last edited by
            #20

            It looks 'the dude' was right. The C++ standard doesn't allow to call main recursively (and states that main 'shall not be used within a program'). Nevertheless, g++ allows that. You have to use -pedantic in order to get a warning.

            "In testa che avete, Signor di Ceprano?" -- Rigoletto

            H 1 Reply Last reply
            0
            • C CPallini

              It looks 'the dude' was right. The C++ standard doesn't allow to call main recursively (and states that main 'shall not be used within a program'). Nevertheless, g++ allows that. You have to use -pedantic in order to get a warning.

              "In testa che avete, Signor di Ceprano?" -- Rigoletto

              H Offline
              H Offline
              honey the codewitch
              wrote on last edited by
              #21

              I don't remember his name and couldn't find the video at gunpoint so "the dude" abides. :laugh:

              Check out my IoT graphics library here: https://honeythecodewitch.com/gfx And my IoT UI/User Experience library here: https://honeythecodewitch.com/uix

              1 Reply Last reply
              0
              • H honey the codewitch

                I believe it never was, as it was meant to be more or less compatible with C code, which doesn't require it. Interestingly you can call main() from inside your C app, but not in C++.

                Check out my IoT graphics library here: https://honeythecodewitch.com/gfx And my IoT UI/User Experience library here: https://honeythecodewitch.com/uix

                M Offline
                M Offline
                megaadam
                wrote on last edited by
                #22

                Agree. Such a requirement would break C compatibility.

                "If we don't change direction, we'll end up where we're going"

                1 Reply Last reply
                0
                • K k5054

                  I have a vague recollection that in K&R days, the value of a function was the value of the last executed statement. so

                  f(x)
                  int x;
                  {
                  x += 3;
                  }

                  would return whatever x+3 evaluated to. I also seem to recall that a function return had to fit in a register. Not sure if either of those are correct. It was a long long time ago. But not in a galaxy far away.

                  "A little song, a little dance, a little seltzer down your pants" Chuckles the clown

                  B Offline
                  B Offline
                  Bruno van Dooren
                  wrote on last edited by
                  #23

                  That is a bit similar to powershell which looks just enough like a programming language to lull you into believing it is. In powershell, the return of a function is any value evaluation that is not assigned to something. And if your function uses function calls, that means it can be anything and everything.

                  1 Reply Last reply
                  0
                  • M Maximilien

                    I see a lot of things like this in the project I'm working on: Was it necessary at some point in time ? Was this an ancient C syntax ?

                    void f(){
                    // .... do something
                    return;
                    }

                    I would not be surprised if I see old K&R syntax somewhere like this

                    void f( a )
                    int a
                    {
                    }

                    CI/CD = Continuous Impediment/Continuous Despair

                    G Offline
                    G Offline
                    glennPattonWork3
                    wrote on last edited by
                    #24

                    Sorry I was under the impression that

                    int fn(){
                    int a;
                    return(0);
                    }

                    was K&R, the cooler

                    void fn
                    {
                    int a;
                    }

                    I though one the rules was 'thou shalt return a value!' Glenn :)

                    1 Reply Last reply
                    0
                    • M Maximilien

                      I see a lot of things like this in the project I'm working on: Was it necessary at some point in time ? Was this an ancient C syntax ?

                      void f(){
                      // .... do something
                      return;
                      }

                      I would not be surprised if I see old K&R syntax somewhere like this

                      void f( a )
                      int a
                      {
                      }

                      CI/CD = Continuous Impediment/Continuous Despair

                      M Offline
                      M Offline
                      mdblack98
                      wrote on last edited by
                      #25

                      In the C89 standard draft (the actual standard you have to buy). Shows that return has never been required....minimalist approach... https://port70.net/~nsz/c/c89/c89-draft.html#3.2.2.2

                      3.6.6.4 The return statement
                      ...
                      Reaching the } that terminates a function is equivalent to executing a return statement without an expression.

                      O 1 Reply Last reply
                      0
                      • M mdblack98

                        In the C89 standard draft (the actual standard you have to buy). Shows that return has never been required....minimalist approach... https://port70.net/~nsz/c/c89/c89-draft.html#3.2.2.2

                        3.6.6.4 The return statement
                        ...
                        Reaching the } that terminates a function is equivalent to executing a return statement without an expression.

                        O Offline
                        O Offline
                        Owen Lawrence
                        wrote on last edited by
                        #26

                        mdblack98 wrote:

                        Reaching the } that terminates a function is equivalent to executing a return statement without an expression.

                        My copy of the 1978 C reference manual contains the equivalent statement: "Flowing off the end of a function is equivalent to a return with no returned value." It also said that if 'return;' form is used, the returned value is undefined. The absence of a type declarator was assumed to mean 'int'. At that time there was no 'void' keyword. So, no need to search earlier than 1978 for the complete answer. - Owen -

                        1 Reply Last reply
                        0
                        • M Maximilien

                          I see a lot of things like this in the project I'm working on: Was it necessary at some point in time ? Was this an ancient C syntax ?

                          void f(){
                          // .... do something
                          return;
                          }

                          I would not be surprised if I see old K&R syntax somewhere like this

                          void f( a )
                          int a
                          {
                          }

                          CI/CD = Continuous Impediment/Continuous Despair

                          J Offline
                          J Offline
                          Juan Pablo Reyes Altamirano
                          wrote on last edited by
                          #27

                          One of my first surprises (in the 90's) going from C++ to C, was that void was never used to define the return value of a main function. C++ had, at that point, always meant to be a superset of C and so had many odd things you wouldn't see in C for years (like variable declarations anywhere in the function). My understanding was that C was always supposed to return a value to the operating system as an integer, regardless of what you did. So when C++ introduced void as a return type, even for main, I guess it was up in the air what you did in the end (that book has since been lost to a basement flooding so I can't remember or look up how it recommended to end the main function)

                          J 1 Reply Last reply
                          0
                          • H honey the codewitch

                            I believe it never was, as it was meant to be more or less compatible with C code, which doesn't require it. Interestingly you can call main() from inside your C app, but not in C++.

                            Check out my IoT graphics library here: https://honeythecodewitch.com/gfx And my IoT UI/User Experience library here: https://honeythecodewitch.com/uix

                            J Offline
                            J Offline
                            jschell
                            wrote on last edited by
                            #28

                            honey the codewitch wrote:

                            Interestingly you can call main() from inside your C app, but not in C++.

                            Odd. Took me a bit to find a reference. Following seems to be best I could find. Use the index to find '3.6' the click on page number. The first section there is the relevant one. https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4296.pdf "The function main shall not be used within a program. The linkage(3.5) of main is implementation-defined. A program that defines main as deleted or that declares main to be inline, static, or constexpr is ill-formed. The name main is not otherwise reserved." Although a draft I did find other mentions to this so I suspect is it substantially correct. Also other references suggest the updated spec matches (2014 to C14). However I think the language of that is not as precise as some might think. Since the linkage is not defined that means a compiler is free to do whatever it wants with it. And the easiest way to handle that is to link it. Why? Because if it doesn't link it then it must figure out that the specific function is in fact the real entry point versus some other legitimate variation. Easier to just ignore the issue - which is allowed. Also note that this restriction was added with newer versions of the spec. The original ANSI spec did not have any subsections in 3.6 at all. ------------------------------------------------- Found the following also. See the second reply. https://stackoverflow.com/questions/2128321/can-main-function-call-itself-in-c[^] I didn't verify that one but the response suggests that the compiler is not responsible for telling you that you should not be calling main. That is another one of things that as a compiler writer should not worry about. There are other things they should spend their time on to get right.

                            H 1 Reply Last reply
                            0
                            • J jschell

                              honey the codewitch wrote:

                              Interestingly you can call main() from inside your C app, but not in C++.

                              Odd. Took me a bit to find a reference. Following seems to be best I could find. Use the index to find '3.6' the click on page number. The first section there is the relevant one. https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4296.pdf "The function main shall not be used within a program. The linkage(3.5) of main is implementation-defined. A program that defines main as deleted or that declares main to be inline, static, or constexpr is ill-formed. The name main is not otherwise reserved." Although a draft I did find other mentions to this so I suspect is it substantially correct. Also other references suggest the updated spec matches (2014 to C14). However I think the language of that is not as precise as some might think. Since the linkage is not defined that means a compiler is free to do whatever it wants with it. And the easiest way to handle that is to link it. Why? Because if it doesn't link it then it must figure out that the specific function is in fact the real entry point versus some other legitimate variation. Easier to just ignore the issue - which is allowed. Also note that this restriction was added with newer versions of the spec. The original ANSI spec did not have any subsections in 3.6 at all. ------------------------------------------------- Found the following also. See the second reply. https://stackoverflow.com/questions/2128321/can-main-function-call-itself-in-c[^] I didn't verify that one but the response suggests that the compiler is not responsible for telling you that you should not be calling main. That is another one of things that as a compiler writer should not worry about. There are other things they should spend their time on to get right.

                              H Offline
                              H Offline
                              honey the codewitch
                              wrote on last edited by
                              #29

                              I hate the specs. They read like bad stereo instructions.

                              Check out my IoT graphics library here: https://honeythecodewitch.com/gfx And my IoT UI/User Experience library here: https://honeythecodewitch.com/uix

                              J 1 Reply Last reply
                              0
                              • H honey the codewitch

                                I hate the specs. They read like bad stereo instructions.

                                Check out my IoT graphics library here: https://honeythecodewitch.com/gfx And my IoT UI/User Experience library here: https://honeythecodewitch.com/uix

                                J Offline
                                J Offline
                                jschell
                                wrote on last edited by
                                #30

                                To be fair though they do provide exactness. Especially the C and C++ ones. I know the Java one has numerous simple documented errors which have remained in place in all versions.

                                1 Reply Last reply
                                0
                                • J Juan Pablo Reyes Altamirano

                                  One of my first surprises (in the 90's) going from C++ to C, was that void was never used to define the return value of a main function. C++ had, at that point, always meant to be a superset of C and so had many odd things you wouldn't see in C for years (like variable declarations anywhere in the function). My understanding was that C was always supposed to return a value to the operating system as an integer, regardless of what you did. So when C++ introduced void as a return type, even for main, I guess it was up in the air what you did in the end (that book has since been lost to a basement flooding so I can't remember or look up how it recommended to end the main function)

                                  J Offline
                                  J Offline
                                  jschell
                                  wrote on last edited by
                                  #31

                                  Juan Pablo Reyes Altamirano wrote:

                                  So when C++ introduced void as a return type, even for main

                                  That statement is some what confusing as phrased. Presumably originally C++ allowed for no return value from main(). Thus for compilation to succeed the type would need to be void. That was because C allowed main to exit without a return value also. The original C recommended a return value. And so does C++. Following is from "The C++ Programming Language Special Edition" section 6.1.5 "Conventionally, main() should return zero if the program terminates normally and nonzero otherwise." And from 3.2 "If no value is returned, the system receive a value indicating successful completion" So it is saying that the program doesn't need to but then a default value will be returned. So it is implicit.

                                  1 Reply Last reply
                                  0
                                  • M Maximilien

                                    I see a lot of things like this in the project I'm working on: Was it necessary at some point in time ? Was this an ancient C syntax ?

                                    void f(){
                                    // .... do something
                                    return;
                                    }

                                    I would not be surprised if I see old K&R syntax somewhere like this

                                    void f( a )
                                    int a
                                    {
                                    }

                                    CI/CD = Continuous Impediment/Continuous Despair

                                    R Offline
                                    R Offline
                                    Ralf Quint
                                    wrote on last edited by
                                    #32

                                    Sorry to burst your bubble on dissing Pascal developers, but in Pascal you do not write void functions, it makes the sane distinction between functions (which return a value) and a procedure (which doesn't). :-D

                                    1 Reply Last reply
                                    0
                                    • M Maximilien

                                      I see a lot of things like this in the project I'm working on: Was it necessary at some point in time ? Was this an ancient C syntax ?

                                      void f(){
                                      // .... do something
                                      return;
                                      }

                                      I would not be surprised if I see old K&R syntax somewhere like this

                                      void f( a )
                                      int a
                                      {
                                      }

                                      CI/CD = Continuous Impediment/Continuous Despair

                                      M Offline
                                      M Offline
                                      Member_16168674
                                      wrote on last edited by
                                      #33

                                      A long way (below) to get to the short version of the answer: No, it was never required and quite on purpose!! C was sort of ALGOL like and to get around one of the most common mechanical errors in assembly language, we forced ALGOL like structure. Some of those errors in assembler came from multiple entry and exit points from subroutines (what we call typed and untyped functions in C). Having an explicit "return" instruction even in an untyped function in C allowed for multiple exits from a function but only *one* entry. This fixed a lot of errors we used to get in assembly language. My opinion is that this is a semi-reasonable thing to do in C. When K&R wrote their initial "White Book" (mostly good for toilet paper!), they intentionally made the closing brace the equivalent of an explicit "return();" or "return;" statement. Remember that C was written to replace assembler on a PDP-8 or PDP-11 from Digital Equipment Corp. Such a machine might have used dual 186 kilobyte 8 inch single sided floppy disks and have maybe 16kB of main memory. To that end, a lot of things like implicit "return" and other things were implemented to save bytes on those floppy disks when the source files were saved. Same reason original C only allowed significance of 6 character function and variable names!!! Too Long; Didn't Read Version: I have been programming in "C" since BSD Unix and System III Unix first came to be available in the wild. Pretty sure early HPUX was a BSD release and where I did most work. Your question as posed cannot be answered because C and C++ are totally different languages and I would go so far as to say "C++" has *never* been a language! Stroustrop *never* got a standard for the initial C++ and standards such as C++17 (not sure I have the number right) look *nothing* like the C++ "things" I used when first using the prototype language versions. My point: C++17 is *NOT* C++ but a separate newer and incompatible language with numerous upgrades, stupid ideas, mistakes, and other differences from C++ as described by Stroustrop in his book. I think I gave my copy of the book to Half Price Books when we downsized our house. It was not uncommon for some of those languages to *require* and explicit return statement or even to require *just one* exit from a function. In some languages, an "untyped function" was instead called a "procedure". Just semantics... Now we have compilers with type checking and *many* other mechanical aids to make arguably correct code that we coul

                                      1 Reply Last reply
                                      0
                                      • M Maximilien

                                        I see a lot of things like this in the project I'm working on: Was it necessary at some point in time ? Was this an ancient C syntax ?

                                        void f(){
                                        // .... do something
                                        return;
                                        }

                                        I would not be surprised if I see old K&R syntax somewhere like this

                                        void f( a )
                                        int a
                                        {
                                        }

                                        CI/CD = Continuous Impediment/Continuous Despair

                                        S Offline
                                        S Offline
                                        sx2008
                                        wrote on last edited by
                                        #34

                                        Early c-compilers could only return values but not expressions. (this was a design flaw of the compiler/c language)

                                        {
                                        int x;
                                        x = 42;
                                        return x; // ok
                                        return x + 1; // does not compile because x + 1 is an expression
                                        return(x + 1); // ok, the expression is evaluated by the compiler

                                        This is why you see the return statement so often together with parentheses even when they aren't required anymore. You should NOT write these unnesseccary parentheses anymore! The return statement is not a function call; just omit the parentheses.

                                        J 1 Reply Last reply
                                        0
                                        • S sx2008

                                          Early c-compilers could only return values but not expressions. (this was a design flaw of the compiler/c language)

                                          {
                                          int x;
                                          x = 42;
                                          return x; // ok
                                          return x + 1; // does not compile because x + 1 is an expression
                                          return(x + 1); // ok, the expression is evaluated by the compiler

                                          This is why you see the return statement so often together with parentheses even when they aren't required anymore. You should NOT write these unnesseccary parentheses anymore! The return statement is not a function call; just omit the parentheses.

                                          J Offline
                                          J Offline
                                          jschell
                                          wrote on last edited by
                                          #35

                                          sx2008 wrote:

                                          You should NOT write these unnesseccary parentheses anymore!

                                          I disagree. You can write a C program on one line by removing those unnecessary end of line characters but that is not a good idea either.

                                          sx2008 wrote:

                                          The return statement is not a function call; just omit the parentheses.

                                          Far as I know no one ever claimed it was.

                                          S 1 Reply Last reply
                                          0
                                          Reply
                                          • Reply as topic
                                          Log in to reply
                                          • Oldest to Newest
                                          • Newest to Oldest
                                          • Most Votes


                                          • Login

                                          • Don't have an account? Register

                                          • Login or register to search.
                                          • First post
                                            Last post
                                          0
                                          • Categories
                                          • Recent
                                          • Tags
                                          • Popular
                                          • World
                                          • Users
                                          • Groups