Passing a structure from a C program to a C DLL

J

Jake Thompson

Hello I created a DLL that has a function that is called from my main c
program.

In my exe I first get a a pointer to the address of the function by
using GetProcAddress and on the dll side I make sure that my function
is being exported by adding a line to the .def file.

This seems to work because when I debug it recognizes the dll and once
it hits the function it goes right into the proper location of the dll.

The problem that I am having is that the function passes a structure as
part of it's three parameters. The structure appears to have all the
correct data in in while its in the main c program. However once it
goes over to the dll the structure no longer has the proper data in it.
It's almost like it was corrupted. What I find odd is that I am
passing a Tag as one of the parameters and that seems to make it over
fine. Can someone tell me what I am doing wrong? My understanding of
GetProcAddress is that once it gets a pointer to the address that it's
just like going from one function to another within the same project.
Of course I could have that misunderstood. Any help would be
appreciated. Below is a sample of my code.

C program

static GENERICCM gencm;

gencm.pszDBName = cszConnect_s;
gencm.pszApplicationName = NULL;
gencm.pszUserID = cu_dbvi__szUserName;
gencm.pszPassword = cu_dbvi__szPassword;
gencm.pszNewPassword = (strlen(cu_dbvi__szNewPassword) ?
cu_dbvi__szNewPassword : NULL);
gencm.pszProxyID = NULL;
gencm.pszProxyScope = NULL;
gencm.fSession = SIM_SS_NORMAL;
gencm.pAsyncCtl = NULL;
lstat = u_generic_cm_call(L"Logon", &gencm, &rc); <--- function that
that is setup to be the pointer to the address in the dll - The first
value is a Tag the second is the structure I am having trouble passing
and the third is a structure that should be passed back

C DLL

struct GENERICCM gencm; <---- identical to the structure that is
passed so that it can be recieved properly

u_dll_generic_cm_call(Tag, gencm, pRC) <-- function that has an
address pointed to it in the C program
if(!wcscmp(Tag,L"Logon"))
{
l_stat = SimLibLogon( gencm.pszDBName, gencm.pszApplicationName,
gencm.pszUserID, gencm.pszPassword, gencm.pszNewPassword,
gencm.pszProxyID, gencm.pszProxyScope, gencm.fSession, gencm.pAsyncCtl,
pRC );
}

As I said I am not sure If I have to do something special to pass the
data. If that is the case can someone enlighten me? Also will I run
into the same problem with the return structure?

Thanks for your help

Jake
 
U

usenet

Jake Thompson said:
The structure appears to have all the correct data in in while its in
the main c program. However once it goes over to the dll the
structure no longer has the proper data in it. It's almost like it
was corrupted. What I find odd is that I am passing a Tag as one of
the parameters and that seems to make it over fine. Can someone tell
me what I am doing wrong? My understanding of GetProcAddress is that
once it gets a pointer to the address that it's just like going from
one function to another within the same project. Of course I could
have that misunderstood. Any help would be appreciated. Below is a
sample of my code.

There is a lot non-standard C in your story (dynamic loading,
GetProcAddress(), etc), but I think that this is not part of your
problem.
static GENERICCM gencm;

[ snipped a lot of struct member initialisation ]
lstat = u_generic_cm_call(L"Logon", &gencm, &rc);

Here you are not passing the structure itself, but the address of the
structure (aka, a pointer to it)
C DLL

struct GENERICCM gencm; <---- identical to the structure that is
passed so that it can be recieved properly

Why are you declaring this structure here ? You also declare a variable
with the same name in your function parameters; this is the one that
will be used inside your function, not the global one.
u_dll_generic_cm_call(Tag, gencm, pRC) <-- function that has an
address pointed to it in the C program

Does this even compile ?
if(!wcscmp(Tag,L"Logon"))
{
l_stat = SimLibLogon( gencm.pszDBName, gencm.pszApplicationName,
gencm.pszUserID, gencm.pszPassword, gencm.pszNewPassword,
gencm.pszProxyID, gencm.pszProxyScope, gencm.fSession, gencm.pAsyncCtl, pRC );
}

It seems that here you are accessing 'gencm' as it were an instance of
your struct, but you passed a *pointer* to the struct earlier.

What I'm missing in your code is a proper prototype definition of your
function, with all the proper types of the arguments. My guess is that
you somehow pass a pointer when you are calling, but you are handling
the argument as if it were a struct, not a pointer.
As I said I am not sure If I have to do something special to pass the
data. If that is the case can someone enlighten me? Also will I run
into the same problem with the return structure?

That depends on how you are returning the structure; if you return a
pointer to a structure, you will have to think about which part of your
program is responsible for allocating and freeing the data.
 
K

Kenny McCormack

Hello I created a DLL that has a function that is called from my main c
program.

Allow me to be the first to say this - and I say it from the deepness of my
heart, with all the kindness and love one has come to associate with the
helpful posts you get in this newsgroup:

Not portable. Can't discuss it here. Blah, blah, blah.
 
G

Grumble

Jake said:
As I said I am not sure If I have to do something special to pass the
data. If that is the case can someone enlighten me? Also will I
run into the same problem with the return structure?

You seem to confuse "struct" and "pointer to struct".

I'll provide a small example.

#include <stdio.h>

struct blah { int a, b, c, d; };

void print_blah(struct blah *ps)
{
printf("%d %d %d %d\n", ps->a, ps->b, ps->c, ps->d);
}

struct blah foo(struct blah s, struct blah *ps)
{
struct blah t = s, u = *ps;

t.a = 12;
ps->c = 15;
u.b = -7;
return t;
}

int main(void)
{
struct blah u = { 1, 2, 3, 4 };
struct blah v = { 5, 6, 7, 8 };
struct blah w = { 0 };
print_blah(&u);
print_blah(&v);
print_blah(&w);
w = foo(u, &v);
print_blah(&u);
print_blah(&v);
print_blah(&w);
return 0;
}
 
J

Jake Thompson

Thanks Grumble and (e-mail address removed)
your advice was helpful - I did goof and pass an address of the
structure when expecting the structure itself. Once I changed the
passed value to the structure itself it worked. I also changed the
naming convention of the dll structure from gencm to gencmdll to make
sure that it was less confusing. I apologize to the others who stated
that I posted to the wrong group but as you can see there was some
overlap so I made a judgement call. Can't say it won't happen again
but I will try to post to the proper group next time.

Jake

BTW it did compile however i did not show all the code only the
important code to save your time
 
J

Jack Klein

Hello I created a DLL that has a function that is called from my main c
program.

[snip]

Sorry, off-topic here. C does not have DLL's, they literally do not
exist in the C language. They are a non-standard extension provided
by your compiler and operating system combination. C does not define
of know or care how they work, your platform defines how they are
supposed to work.

Ask in where the experts on
this sort of thing hang out.
 
M

Mike Wahler

Jake Thompson said:
Thanks Grumble and (e-mail address removed)
your advice was helpful - I did goof and pass an address of the
structure when expecting the structure itself. Once I changed the
passed value to the structure itself it worked. I also changed the
naming convention of the dll structure from gencm to gencmdll to make
sure that it was less confusing. I apologize to the others who stated
that I posted to the wrong group but as you can see there was some
overlap so I made a judgement call. Can't say it won't happen again
but I will try to post to the proper group next time.

First, you can ignore remarks by Kenny, our resident troll.

But do note that much of your posted code is indeed nonstandard.
However a couple people have taken the trouble to identify the
fact that yours was indeed a language problem. Not everyone
is always willing or able to spend the time to do so.
Jake

BTW it did compile however i did not show all the code only the
important code to save your time

The best way to save the readers' time is to present the
problem with only standard code which still conveys the
issue in question. In this case you could have created
a 'dummy' struct type to stand in for the nonstandard one
(or provided the definition of the nonstandard one --
but this isn't always feasible, due to e.g. it might
be very large, copyright issues, etc.).


-Mike
 
I

Ico

Mike Wahler said:
The best way to save the readers' time is to present the problem with
only standard code which still conveys the issue in question. In this
case you could have created a 'dummy' struct type to stand in for the
nonstandard one

There's another positive effect of doing this: often I find myself
gaining insight in the cause of a problem, just at the moment I am
isolating and simplifying the offensive piece of code to show to a
collegue or posting to a newsgroup.

Ico
 
Joined
Feb 18, 2011
Messages
1
Reaction score
0
USELESS

Kenny McCormack said:
In article <[email protected]>,
Jake Thompson <[email protected]> wrote:
>Hello I created a DLL that has a function that is called from my main c
>program.


Allow me to be the first to say this - and I say it from the deepness of my
heart, with all the kindness and love one has come to associate with the
helpful posts you get in this newsgroup:

Not portable. Can't discuss it here. Blah, blah, blah.

What a lame and useless post. Why the hell did you bothered to write? Nothing better to do, heh? Please, next time keep your kindness and deepness for yourself and write something only if it can be of help to others, otherwise you'll just prove that you're a complete ass :withstup:

PS. here I am answering to this ass with another usless post, but I cannot help it :) I was bothered by a similar problem to Jake's and while I was hoping for an enlightening answer I end up reading kenny's ****. So annoying.
 

Ask a Question

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

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,764
Messages
2,569,567
Members
45,041
Latest member
RomeoFarnh

Latest Threads

Top