Re: Same code problem
- From: "Pavel A." <pavel_a@xxxxxxxxxxxxxxx>
- Date: Thu, 22 Jan 2009 18:54:32 +0200
Ah. The PIC compiler uses so called "compiled stack",
and probably, some weirdness about pointers as well
(like several address spaces, pointers to which are
not compatible types).
Godd luck with that... :(
--pa
Robby wrote:
Hello,.
Yup its since early December that I am still trying to complete this snippit of code because I am trying to accomodate my *special* compiler. I am sure you all know it by now. The vendor tells me I cannot use forwards declarations as we did in previous sample codes. Also, I should not use void * as members. Hum!!!
This is becoming a crosswaord puzzel between the do's and don'ts of two compilers. Here is the reccomendations, perhaps someone can figure out a work around... because I would need much more experience with typedef's and forwards declarations to figure this one on my own.
At this point its no use I show the code in VC++ because whatever we get to compile in VC++ might not compile exactly the same way in the pic compiler. So based on some reccomendations, that I may not quite be good enough to figure out, I unfortunately asking this community for help. Please view some of the vendor's reccomendations at the end of this post.
Here again is the very familar code I am trying to get to compile without errors in the PIC conpiler:
=================================krn.h
typedef long *LRESULT;
typedef long WPARAM;
typedef long LPARAM;
typedef struct tagHwnd{
void *handle; } HWND;
typedef LRESULT (*WNDPROC)(HWND, long, WPARAM, LPARAM);
typedef struct tagWnd{ WNDPROC lpfnWndProc;
int style;
long backGround;
long titleMsg; long extra;
} WND, *pWND;
typedef struct tagRwp{ HWND hwnd;
int showWinEnable;
} RWP;
typedef struct tagMsg{
HWND hwnd;
long msg;
WPARAM wParam;
LPARAM lParam;
long time;
} KM_MSG, *pKM_MSG;
RWP rwp[3] = {0,0,0,0,0,0};
void ULC_KERNEL_dispatch_message(KM_MSG *K);
=================================krn.c
#include <stdlio.h> // CCS LIBRARY STANDARD LIBRARY
#include <KERNEL.h> // KERNEL HEADER FILE!
LRESULT KWP(HWND x, long m, WPARAM w, LPARAM l); LRESULT callerFunction(WNDPROC vWNDPROC, HWND h, long m, WPARAM w, LPARAM l);
void main()
{
KM_MSG u; // Create an KM_MSG object
pKM_MSG msg = &u; // Assign the address of KM_MSG object WND wnd; // Create a WND object
// DEFINE A WINDOW!
wnd.lpfnWndProc = KWP; // Assign a function pointer ! (Assigns function KWP )
wnd.style = 0; // Assign other stuff...
// Assign the address of a wnd object to the void pointer called "handle" which is a // member of tagHwnd structure
(rwp[0].hwnd).handle = &wnd;
msg->hwnd = rwp[0].hwnd; // Assign the void pntr to another hwnd ULC_KERNEL_dispatch_message(msg); // Pass a pointer to a msg object
}
void ULC_KERNEL_dispatch_message(KM_MSG *msg) {
LRESULT zzz;
// Call the correct function based on contents of the function pntr in "lpfnWndProc"
zzz = callerFunction(((msg->hwnd).handle)->lpfnWndProc, msg->hwnd, msg->msg, msg->wParam, msg->lParam);
}
//CALLBACK FUNCTION IMPLEMENTATION <<< Line 38 LRESULT callerFunction(WNDPROC vWNDPROC, HWND h, long m, WPARAM w, LPARAM l)
{ return (*vWNDPROC) (h, m, w, l); //<<< Line 41
}
LRESULT KWP(HWND x, long m, WPARAM w, LPARAM l) { //... other code ...
return 0;
}
=======================================
Here's what I am suggested to do by my vendor:
1. Change:
LRESULT callerFunction(LRESULT (*WNDPROC) (HWND, long, WPARAM, LPARAM), HWND h, long m, WPARAM w, LPARAM l);
To:
LRESULT callerFunction(WNDPROC vWNDPROC, HWND h, long m, WPARAM w, LPARAM l);
*** Which I have done so!
2. And line 41 should be:
{ return (*vWNDPROC)(h, m, w, l);
***Which I have done so!
3. The line below line 38, you can not typecase a function pointer like this :
zzz = callerFunction(((struct tagWnd*) (msg->hwnd).handle)->lpfnWndProc, msg->hwnd, msg->msg, msg->wParam, msg->lParam);
because the compiler needs to know the call tree at compile time so it allocate the stack frame (we don't have a true stack on the PIC). You will be OK as long as you make all you compatible function pointers of the correct type (use a typedef to be sure). Don't try to convert a void * at run time to a function pointer because there is no way to know how to pass the parametters.
*** Which I have done so!
He aslo says:
You are right in that you can not use "void *handle" to point to a function.
You can forward declare pointers in a typedef, like this:
typedef node * pnode;
struct node {
pnode next;
int a,b,c;
};
=============================================
Now, I don't know how to make the link between what they are suggesting and the typedefs that I have at the top of my header... ?
Here is what I tried:
typedef HWND * vHWND;
typedef struct tagHwnd{
//void *handle; vHWND handle;
} HWND;
And now I got an error at the following line:
zzz = callerFunction(((msg->hwnd).handle)->lpfnWndProc, msg->hwnd, msg->msg, msg->wParam, msg->lParam);
it points to "lpfnWndProc" and says "Previous identifier must be a pointer!
And here I tried accessing the lpfnWndProc in different ways but now I hit a wall!
I know some stuff about forwards declarations and typedef's but I don't know how I could get around this using the vendor's suggestions. I posted this to him also and awaiting a reply.
Anyone with some ideas on this. This would be really helpfull. All help sincerely appreciated...
- References:
- Same code problem
- From: Robby
- Same code problem
- Prev by Date: Re: security descriptor
- Next by Date: Re: Checked iterators not standard C++? Porting code from VS6 to VS2008
- Previous by thread: Same code problem
- Next by thread: Re: Same code problem
- Index(es):
Relevant Pages
|