Discussion:
"PORTING C" > Function Pointers issue.
(too old to reply)
Robby
2009-12-23 22:21:01 UTC
Permalink
Hello,

I give up! This used to work! Now I get errors.

I have looked at it all afternoon and tried everything forwards and backwards!

I haven't used function pointers for quite a while, but all of this compiled
back then.
So again, I watered down code. I don't get it, the pointer to functions
declaration is typedefed after all the typedefed structures. And the arrays
of function pointers is declared right after that. And then I declared the
function prototype right after that.

Here are the errors I get:

c(1) : error C2061: syntax error : identifier 'CALLBACK_WP_INTRO
1>c:\_dts_programming\pic\_microchip_issues\vc++\function_pointers\function_pointers\wp_intro.c(1) : error C2059: syntax error : ';'
1>c:\_dts_programming\pic\_microchip_issues\vc++\function_pointers\function_pointers\wp_intro.c(1)
: error C2146: syntax error : missing ')' before identifier 'hwnd
1>c:\_dts_programming\pic\_microchip_issues\vc++\function_pointers\function_pointers\wp_intro.c(1) : error C2061: syntax error : identifier 'hwnd
1>c:\_dts_programming\pic\_microchip_issues\vc++\function_pointers\function_pointers\wp_intro.c(1) : error C2059: syntax error : ',
1>c:\_dts_programming\pic\_microchip_issues\vc++\function_pointers\function_pointers\wp_intro.c(1) : error C2059: syntax error : ')'


Here is the code:
===============KERNEL.h
typedef long *LRESULT;
typedef long WPARAM;
typedef long LPARAM;

typedef struct tagHwnd {
long caption_msg;
} HWND;

typedef struct tagMsg {
HWND hwnd;
long msg;
WPARAM wParam;
LPARAM lParam;
long time;
} KM_MSG;


// Pointer to function declaration (Used for callbacks!)
typedef LRESULT(*callBack)(HWND hwnd, long message, WPARAM w, LPARAM l);

callBack cb[1]; // Array of function pointers

// Function declaration!
LRESULT CALLBACK_WP_INTRO(HWND hwnd, long message, WPARAM wParam, LPARAM
lParam);

===============KERNEL.c
#include <stdio.h>
#include "KERNEL.h"

int main(void)
{
KM_MSG m;
HWND hwnd;

hwnd.caption_msg = 1;
m.msg = 1;
m.lParam = 2;
m.wParam = 3;

cb[0] = CALLBACK_WP_INTRO;
CALLBACK_WP_INTRO(hwnd, m.msg, m.wParam, m.lParam);
}

===============WP_INTRO.c
LRESULT CALLBACK_WP_INTRO(HWND hwnd, long message, WPARAM wParam, LPARAM
lParam)
{return 0; }
==========================


But if I do this, it compiles without errors ??

===============KERNEL.h
typedef long *LRESULT;
typedef long WPARAM;
typedef long LPARAM;

typedef struct tagHwnd {
long caption_msg;
} HWND;

typedef struct tagMsg {
HWND hwnd;
long msg;
WPARAM wParam;
LPARAM lParam;
long time;
} KM_MSG;


// Pointer to function declaration (Used for callbacks!)
typedef LRESULT(*callBack)(HWND hwnd, long message, WPARAM w, LPARAM l);

callBack cb[1]; // Array of function pointers

// Function declaration!
LRESULT CALLBACK_WP_INTRO(HWND hwnd, long message, WPARAM wParam, LPARAM
lParam);

===============KERNEL.c
#include <stdio.h>
#include "KERNEL.h"

LRESULT CALLBACK_WP_INTRO(HWND hwnd, long message, WPARAM wParam, LPARAM
lParam)
{return 0; }

int main(void)
{
KM_MSG m;
HWND hwnd;

hwnd.caption_msg = 1;
m.msg = 1;
m.lParam = 2;
m.wParam = 3;

cb[0] = CALLBACK_WP_INTRO;
CALLBACK_WP_INTRO(hwnd, m.msg, m.wParam, m.lParam);
}
==========================

All help sincerely appreciated!!
Robert
Igor Tandetnik
2009-12-23 22:36:17 UTC
Permalink
Post by Robby
===============KERNEL.h
// Pointer to function declaration (Used for callbacks!)
typedef LRESULT(*callBack)(HWND hwnd, long message, WPARAM w, LPARAM l);
callBack cb[1]; // Array of function pointers
Don't define variables in headers.
Post by Robby
===============WP_INTRO.c
LRESULT CALLBACK_WP_INTRO(HWND hwnd, long message, WPARAM wParam, LPARAM
lParam)
{return 0; }
Since you haven't included KERNEL.h here, the compiler doesn't know what LRESULT or HWND or WPARAM or LPARAM are.
Post by Robby
But if I do this, it compiles without errors ??
===============KERNEL.c
#include <stdio.h>
#include "KERNEL.h"
LRESULT CALLBACK_WP_INTRO(HWND hwnd, long message, WPARAM wParam, LPARAM
lParam)
{return 0; }
Here you did include KERNEL.h, so the compiler does know what LRESULT or HWND or WPARAM or LPARAM are.
--
With best wishes,
Igor Tandetnik

With sufficient thrust, pigs fly just fine. However, this is not necessarily a good idea. It is hard to be sure where they are going to land, and it could be dangerous sitting under them as they fly overhead. -- RFC 1925
Robby
2009-12-24 21:25:01 UTC
Permalink
Hello Igor,

Darn global stuff, gets me everytime! :-)
Post by Igor Tandetnik
Post by Robby
===============KERNEL.h
// Pointer to function declaration (Used for callbacks!)
typedef LRESULT(*callBack)(HWND hwnd, long message, WPARAM w, LPARAM l);
callBack cb[1]; // Array of function pointers
Don't define variables in headers.
Sincerely Igor, I don't see how the language treats "callback cb[1];" as a
variable definition? But then what do I know... right!

Isn't:

callBack cb[1];

a "declaration" of an array holding 1 function pointer of type callback ???
I don't see where I defined anything here? I mean I didn't do something like
this:

cb[0] = CALLBACK_WP_INTRO;

Which would imply that I **defined/assigned** something to the array !!!!

And also:

Isn't:

int x;

a variable *declaration* and shouldn't,

int x = 2;

be considered as a variable *definition*, because the latter is defining
what x is to be which is 2 ? The former instead just declares x.

Please do get get back, I would like to iron out these simple vexatious
details once and for all.
Post by Igor Tandetnik
Post by Robby
===============WP_INTRO.c
LRESULT CALLBACK_WP_INTRO(HWND hwnd, long message, WPARAM wParam, LPARAM
lParam)
{return 0; }
Since you haven't included KERNEL.h here, the compiler doesn't know what LRESULT or HWND or WPARAM or LPARAM are.
Okay, understood! I'll get used to it!
Post by Igor Tandetnik
Post by Robby
But if I do this, it compiles without errors ??
===============KERNEL.c
#include <stdio.h>
#include "KERNEL.h"
LRESULT CALLBACK_WP_INTRO(HWND hwnd, long message, WPARAM wParam, LPARAM
lParam)
{return 0; }
Here you did include KERNEL.h, so the compiler does know what LRESULT or HWND or WPARAM or LPARAM are.
Understood.

Thankyou for helping me!

Regards
Rob
Igor Tandetnik
2009-12-24 23:14:01 UTC
Permalink
Post by Robby
callBack cb[1];
a "declaration" of an array holding 1 function pointer of type callback ???
No, it's a definition (well, formally, it's a declaration that is also a definition). A declaration would look like this:

extern callback cb[1];
Post by Robby
I don't see where I defined anything here? I mean I didn't do something like
cb[0] = CALLBACK_WP_INTRO;
This is neither a declaration nor a definition. It's a statement. It doesn't introduce a new name, nor cause storage to be allocated.
Post by Robby
Which would imply that I **defined/assigned** something to the array !!!!
Definition and assignment are two entirely different, largely unrelated things. You can define a variable only once in the program, but you can assign a new value to it multiple times.
Post by Robby
int x;
a variable *declaration* and shouldn't,
int x = 2;
be considered as a variable *definition*
Both are definitions, one with an initializer and one without (and thus implicitly initialized to 0, assuming it's a global variable).
Post by Robby
because the latter is defining
what x is to be which is 2 ?
Not defining - initializing. Again, when defining a global variable, "int x;" is equivalent to "int x = 0;". On the other hand, this would be a declaration:

extern int x;
--
With best wishes,
Igor Tandetnik

With sufficient thrust, pigs fly just fine. However, this is not necessarily a good idea. It is hard to be sure where they are going to land, and it could be dangerous sitting under them as they fly overhead. -- RFC 1925
Robby
2009-12-25 02:07:01 UTC
Permalink
Thanks Igor,

On another note, I was browsing for some function pointer samples on the
Internet and I came across a sample at:

http://stackoverflow.com/questions/252748/how-to-use-array-of-function-pointers

Its the 2nd sample that concerns me which looks like this:
========================================
void fun1()
{

}
void fun2()
{

}
void fun3()
{

}

void (*func_ptr[3]) = {fun1, fun2, fun3};

main()
{
int option;
printf("\nEnter function number u want");
printf("\nyou should not enter other than 0 , 1, 2"); /*bcos we hav only 3
functions*/

scanf("%d",&option);

if((option>=0)&&(option<=2))
{
(*func_ptr[option])();
}
return 0;
}
==================================

Does this compile at your end... cause I get errors on this sample.

The reason I ask also is that I was wondering if we can really initialize an
array of pointers all in one line like they did at the following line:

void (*func_ptr[3]) = {fun1, fun2, fun3};

For me it seems weird ! shouldn't it of been:

void (*func_ptr[3]) (...parameter list...) ;

Asides from the lack of inclusions there is an error that points to the
following line:

(*func_ptr[option])();

here's the error:

c:\_dts_code_testing\_testing_personal_samples\function_pointers\function_pointers\t.c(29) : error C2100: illegal indirection

Thanks for your help.
--
Best regards
Roberto
Igor Tandetnik
2009-12-25 06:55:03 UTC
Permalink
Post by Robby
On another note, I was browsing for some function pointer samples on the
http://stackoverflow.com/questions/252748/how-to-use-array-of-function-pointers
void (*func_ptr[3]) = {fun1, fun2, fun3};
It's a typo. It's supposed to be

void (*func_ptr[3])() = {fun1, fun2, fun3};

Note an extra pair of parentheses.
--
With best wishes,
Igor Tandetnik

With sufficient thrust, pigs fly just fine. However, this is not necessarily a good idea. It is hard to be sure where they are going to land, and it could be dangerous sitting under them as they fly overhead. -- RFC 1925
Barry Schwarz
2009-12-25 08:27:25 UTC
Permalink
On Fri, 25 Dec 2009 01:55:03 -0500, "Igor Tandetnik"
Post by Igor Tandetnik
Post by Robby
On another note, I was browsing for some function pointer samples on the
http://stackoverflow.com/questions/252748/how-to-use-array-of-function-pointers
void (*func_ptr[3]) = {fun1, fun2, fun3};
It's a typo. It's supposed to be
void (*func_ptr[3])() = {fun1, fun2, fun3};
Note an extra pair of parentheses.
It's amazing that he found this brain dead example among all the
correct ones (at least syntactically) that google displays.
--
Remove del for email
Robby
2009-12-26 02:07:01 UTC
Permalink
Post by Igor Tandetnik
Post by Robby
On another note, I was browsing for some function pointer samples on the
http://stackoverflow.com/questions/252748/how-to-use-array-of-function-pointers
void (*func_ptr[3]) = {fun1, fun2, fun3};
It's a typo. It's supposed to be
void (*func_ptr[3])() = {fun1, fun2, fun3};
Note an extra pair of parentheses.
Thanks Igor.

Rob

Continue reading on narkive:
Loading...