[comp.lang.c] Passing functions in C

brad@SSD.CSD.HARRIS.COM (Brad Appleton) (03/13/90)

Sorry to post this folks!
I tried e-mail to both of her addresses but both bounced :-(


In article <1990Mar9.045151.9601@ucselx.sdsu.edu> cynthia@ucselx.sdsu.edu (cynthia Anderson) writes:
>hello
>
>i would like to be able to write a procedure that takes as
>a parameter a procedure name and then using that name
>calls the procedure.
>
>ie  runAProcedure(myProcedure)
>   {
>
>
>	myProcedure
>
>
>}
>
>Is this possible to do in C?  Any help or advise is appreciated
>tho please e-mail responses so the net won't be cluttered.
>
>thanks,
>
>cynthia anderson
><cynthia@cod.nosc.mil.uucp>
>or
><cynthia@ucselx.sdsu.edu>
>
>Disclaimer: whenever it was and whenever it happened, i'm sure i 
>wasn't there and it couldn't have been me.

NO! It is not possible to do in C! (Im pretty sure you cant do this
in ANSI C either). 

What you can do is pass the address of a function to another function
and call that function:

     int runAfunct( myfunct )
       int (*myfunct)();
     {
        (*myfunct)();
     }

     int someFunct()
     {
       return 10;
     }

     main()
     {
       int  i;

       i = runAfunct( someFunct );
       printf( "%d\n", i );

       exit( 0 );
     }

 
Hope this helps!!!

+=-=-=-=-=-=-=-=-= "... and miles to go before I sleep." -=-=-=-=-=-=-=-=-=-+
|  Brad Appleton                       |  Harris Computer Systems Division  |
|                                      |  2101  West  Cypress  Creek  Road  |
|      brad@ssd.csd.harris.com         |  Fort  Lauderdale, FL  33309  USA  |
|     ... {uunet | novavax}!hcx1!brad  |  MailStop 161      (305) 973-5007  |
+=-=-=-=-=-=-=-=- DISCLAIMER: I said it, not my company! -=-=-=-=-=-=-=-=-=-+

brad@SSD.CSD.HARRIS.COM (Brad Appleton) (03/13/90)

OOPS -- I screwed up! the body of function "runAfunct" in my
previous post should have been "return (*myfunct)();" 
not "(*myfunct)();" without the return !!!

My most sincere apologies.

incidentally, that brings up an interesting point! If I have a function

   int foo() { int i; i = 10; }

without a specified return value, what will be returned when foo is called.
On one compiler I have used, it will return "10" because 10 was the last
"thing that was evaluated". I doubt that this is reliable however (is it?)

Should the compiler catch the "missing return" or is that left strictly
to lint?

advTHANXance

+=-=-=-=-=-=-=-=-= "... and miles to go before I sleep." -=-=-=-=-=-=-=-=-=-+
|  Brad Appleton                       |  Harris Computer Systems Division  |
|                                      |  2101  West  Cypress  Creek  Road  |
|      brad@ssd.csd.harris.com         |  Fort  Lauderdale, FL  33309  USA  |
|     ... {uunet | novavax}!hcx1!brad  |  MailStop 161      (305) 973-5007  |
+=-=-=-=-=-=-=-=- DISCLAIMER: I said it, not my company! -=-=-=-=-=-=-=-=-=-+

CMH117@psuvm.psu.edu (Charles Hannum) (03/14/90)

In article <3243@hcx1.SSD.CSD.HARRIS.COM>, brad@SSD.CSD.HARRIS.COM (Brad
Appleton) says:
>
>incidentally, that brings up an interesting point! If I have a function
>
>   int foo() { int i; i = 10; }
>
>without a specified return value, what will be returned when foo is called.
>On one compiler I have used, it will return "10" because 10 was the last
>"thing that was evaluated". I doubt that this is reliable however (is it?)
>
>Should the compiler catch the "missing return" or is that left strictly
>to lint?

Old style C compilers that did not support the void type simply used int
functions that didn't return a value.  Thus, out of habit, some compilers
*still* don't catch missing return values.  There should at least be a
warning you can turn on that will catch this, though you should be able
to turn it off when working with old C programs.

>advTHANXance

Cute.


Virtually,
- Charles Martin Hannum II       "Klein bottle for sale ... inquire within."
    (That's Charles to you!)     "To life immortal!"
  cmh117@psuvm.{bitnet,psu.edu}  "No noozzzz izzz netzzzsnoozzzzz..."
  c9h@psuecl.{bitnet,psu.edu}    "Mem'ry, all alone in the moonlight ..."

karl@haddock.ima.isc.com (Karl Heuer) (03/14/90)

In article <3243@hcx1.SSD.CSD.HARRIS.COM> brad@SSD.CSD.HARRIS.COM (Brad Appleton) writes:
>[The function   int foo() { int i; i = 10; }   will, on some compilers,
>appear to have returned the value 10.  Unreliable?]

Very.  What you're actually getting is whatever happened to be left lying
around in the function-return-value register.

>Should the compiler catch the "missing return" or is that left strictly
>to lint?

As far as the language definition goes, there is no distinction between cc and
lint.  This check is traditionally done only in lint because it generally
requires cross-module analysis to know whether the value that isn't returned
from foo() is actually being used anywhere.

If it *isn't* being used, then the code is legal but sloppy (it should be
declared "void").  This remains legal for for backward compatibility, and,
unfortunately, a lot of code continues to depend on it.

Karl W. Z. Heuer (karl@ima.ima.isc.com or harvard!ima!karl), The Walking Lint

gordon@sneaky.UUCP (Gordon Burditt) (03/15/90)

>>i would like to be able to write a procedure that takes as
>>a parameter a procedure name and then using that name
>>calls the procedure.
>>
>>ie  runAProcedure(myProcedure)
>>   {
>>	myProcedure
>>}
>>
>>Is this possible to do in C?  Any help or advise is appreciated
>>tho please e-mail responses so the net won't be cluttered.
>
>NO! It is not possible to do in C! (Im pretty sure you cant do this
>in ANSI C either). 

Yes, it is.  Some really old compilers did accept myfunct(), where
myfunct is of type pointer-to-function-returning-something, as meaning
the same as (*myfunct)().  Modern compilers tend to at least give
warnings about it.

From section 3.7.1 of the Jan 1988 ANSI C draft (sorry, that's the most
recent one I have):
QUOTE

To pass one function to another, one might say
	int f(void)
	/* ... */
	g(f);

Note that f must be declared explicitly in the calling function, as
its appearance in the expression g(f) was not followed by (.
Then the definition of g might read

	g(int (*funcp)(void))
	{
		/* ... */ (*funcp)() /* or funcp() ... */
	}
or, equivalently,
	g(int func(void))
	{
	/* ... */ func() /* or (*func)() ... */
	}

END QUOTE.

ANSI allows this, and even gives an example of it.

						Gordon L. Burditt
						sneaky.lonestar.org!gordon