Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C Programming > error when allocating memory using a pointer inside a struct via a function

Reply
Thread Tools

error when allocating memory using a pointer inside a struct via a function

 
 
elmafiacs@yahoo.es
Guest
Posts: n/a
 
      02-22-2005
I need some help with an error I'm getting...
Sorry if this is basic stuff, but I'm still a newbie on C programming
(working up, though).
Also, I'm using gcc as my compiler ('gcc t.c -o t', no strange stuff).
Sorry about the long subject, I didn't know how to explain it better...

struct small {
int num;
};

struct big {
struct small *small_thing;
};

void f(struct small **s)
{
s = malloc(sizeof(struct small));
memset(s, 0, sizeof(struct small));
s->num = 42;
}

main()
{
struct big *big_thing;

big_thing = malloc(sizeof(struct big));
memset(&big_thing, 0, sizeof(struct big));

f(&big_thing->small_thing);
printf("%i\n", big_thing->small_thing->n);
}

But when I do:
s->num = 42;
the compiler fails with error 'request for member 'num' in something
not an structure or union', and I don't know why.

I tried this way:

void f(struct small **s)
{
struct small *s_ptr;
s_ptr->num = 42;
memcpy(s, &s_ptr, sizeof(struct small));
}

I'm not sure, but I think that the second function is unnecessary. So,
how to fix the first function?

Thanks.

 
Reply With Quote
 
 
 
 
David Resnick
Guest
Posts: n/a
 
      02-22-2005
http://www.velocityreviews.com/forums/(E-Mail Removed) wrote:

> I need some help with an error I'm getting...
> Sorry if this is basic stuff, but I'm still a newbie on C programming
> (working up, though).
> Also, I'm using gcc as my compiler ('gcc t.c -o t', no strange stuff).
> Sorry about the long subject, I didn't know how to explain it better...
>
> struct small {
> int num;
> };
>
> struct big {
> struct small *small_thing;
> };
>
> void f(struct small **s)
> {
> s = malloc(sizeof(struct small));
> memset(s, 0, sizeof(struct small));
> s->num = 42;
> }
>


s is a pointer to a pointer to a struct small, not a pointer
to a struct small. Accordingly, you want this:

*s = malloc(sizeof **s);
memset(*s, 0, sizeof **s);
(*s)->num = 42;

And you should check the return value of malloc...

-David



-David
 
Reply With Quote
 
 
 
 
Martin Ambuhl
Guest
Posts: n/a
 
      02-22-2005
(E-Mail Removed) wrote:
> I need some help with an error I'm getting...
> Sorry if this is basic stuff, but I'm still a newbie on C programming
> (working up, though).
> Also, I'm using gcc as my compiler ('gcc t.c -o t', no strange stuff).
> Sorry about the long subject, I didn't know how to explain it better...
>
> struct small {
> int num;
> };
>
> struct big {
> struct small *small_thing;
> };
>
> void f(struct small **s)
> {
> s = malloc(sizeof(struct small));
> memset(s, 0, sizeof(struct small));
> s->num = 42;
> }
>
> main()
> {
> struct big *big_thing;
>
> big_thing = malloc(sizeof(struct big));
> memset(&big_thing, 0, sizeof(struct big));
>
> f(&big_thing->small_thing);
> printf("%i\n", big_thing->small_thing->n);
> }
>
> But when I do:
> s->num = 42;
> the compiler fails with error 'request for member 'num' in something
> not an structure or union', and I don't know why.
>
> I tried this way:
>
> void f(struct small **s)
> {
> struct small *s_ptr;
> s_ptr->num = 42;
> memcpy(s, &s_ptr, sizeof(struct small));
> }
>
> I'm not sure, but I think that the second function is unnecessary. So,
> how to fix the first function?
>
> Thanks.
>


Please don't post code that is not that which you have actually
compiled. Here is a start toward fixing your code:
#include <stdlib.h>
#include <stdio.h>
#include <string.h>

struct small
{
int num;
};

struct big
{
struct small *small_thing;
};

void f(struct small **s)
{
*s = malloc(sizeof **s);
/* add code to check that *s != 0 */
memset(*s, 0, sizeof **s);
(*s)->num = 42;
}

int main(void)
{
struct big *big_thing;

big_thing = malloc(sizeof *big_thing);
/* add code to check that big_thing != 0 */
memset(&big_thing, 0, sizeof big_thing);

f(&big_thing->small_thing);
printf("%i\n", big_thing->small_thing->num);
free(big_thing->small_thing);
free(big_thing);
return 0;
}



 
Reply With Quote
 
elmafiacs@yahoo.es
Guest
Posts: n/a
 
      02-22-2005
Thanks for the help.

 
Reply With Quote
 
Al Bowers
Guest
Posts: n/a
 
      02-22-2005
Martin Ambuhl wrote:

>
> Please don't post code that is not that which you have actually
> compiled. Here is a start toward fixing your code:


In addition to compiling, run and testing the code before posting can be
helpful
(but not final) in catching additional flaws. For example....

> #include <stdlib.h>
> #include <stdio.h>
> #include <string.h>
>
> struct small
> {
> int num;
> };
>
> struct big
> {
> struct small *small_thing;
> };
>
> void f(struct small **s)
> {
> *s = malloc(sizeof **s);
> /* add code to check that *s != 0 */
> memset(*s, 0, sizeof **s);
> (*s)->num = 42;
> }
>
> int main(void)
> {
> struct big *big_thing;
>
> big_thing = malloc(sizeof *big_thing);
> /* add code to check that big_thing != 0 */
> memset(&big_thing, 0, sizeof big_thing);
>

Running and testing might identify the memset statement flaw
above. It should be:
memset(big_thing, 0 , sizeof big_thing);

And, as you suggested, code to catch dynamic memory allocations
with function malloc needs to be added to make execution of the code
safe. See the example below:

> f(&big_thing->small_thing);
> printf("%i\n", big_thing->small_thing->num);
> free(big_thing->small_thing);
> free(big_thing);
> return 0;
> }
>

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

struct small {
int num;
};

struct big {
struct small *small_thing;
};

void f(struct small **s)
{
*s = malloc(sizeof(struct small));
if(*s)
{
memset(*s, 0, sizeof(struct small));
(*s)->num = 42;
}
}

int main(void)
{
struct big *big_thing;

big_thing = malloc(sizeof(struct big));
if(big_thing)
{
memset(big_thing, 0, sizeof(struct big));
f(&big_thing->small_thing);
if(big_thing->small_thing)
printf("big_thing->small_thing->num = %i\n",
big_thing->small_thing->num);
free(big_thing->small_thing);
}
free(big_thing);
return 0;
}

Al Bowers
 
Reply With Quote
 
Old Wolf
Guest
Posts: n/a
 
      02-22-2005
Al Bowers wrote:
> Martin Ambuhl wrote:
> >
> > Please don't post code that is not that which you have actually
> > compiled. Here is a start toward fixing your code:

>
> > struct big *big_thing;
> >
> > big_thing = malloc(sizeof *big_thing);
> >
> > memset(&big_thing, 0, sizeof big_thing);

>
> Running and testing might identify the memset statement flaw
> above. It should be:
> memset(big_thing, 0 , sizeof big_thing);
>


1) Running and testing isn't a great way of checking for
undefined behaviour

2) A statement: memset(foo, bar, sizeof foo); is wrong, unless
foo and &foo are the same address (ie. for an array).
It should be:

memset(big_thing, 0, sizeof *big_thing);

The OP (who has been snipped) had it correct.
IMHO, even better would be to use calloc instead of malloc.

 
Reply With Quote
 
Al Bowers
Guest
Posts: n/a
 
      02-22-2005
Old Wolf wrote:

>Al Bowers wrote:
>
>
>>Martin Ambuhl wrote:
>>
>>
>>>Please don't post code that is not that which you have actually
>>>compiled. Here is a start toward fixing your code:
>>>
>>>
>>> struct big *big_thing;
>>>
>>> big_thing = malloc(sizeof *big_thing);
>>>
>>> memset(&big_thing, 0, sizeof big_thing);
>>>
>>>

>>Running and testing might identify the memset statement flaw
>>above. It should be:
>>memset(big_thing, 0 , sizeof big_thing);
>>
>>
>>

>
>
>2) A statement: memset(foo, bar, sizeof foo); is wrong, unless
>foo and &foo are the same address (ie. for an array).
>It should be:
>
> memset(big_thing, 0, sizeof *big_thing);
>
>The OP (who has been snipped) had it correct.
>
>
>

I don't think so. The op code was:

> struct big *big_thing;


> big_thing = malloc(sizeof(struct big));
> memset(&big_thing, 0, sizeof(struct big));


Is that correct?

I believe it should be:
memset(big_thing, 0, sizeof *big_thing);
or
memset(big_thing, 0, sizeof(struct big));
 
Reply With Quote
 
Old Wolf
Guest
Posts: n/a
 
      02-23-2005
Al Bowers wrote:
> Old Wolf wrote:
> >
> >It should be:
> >
> > memset(big_thing, 0, sizeof *big_thing);
> >
> >The OP (who has been snipped) had it correct.
> >

> I don't think so. The op code was:
>
> > struct big *big_thing;
> > big_thing = malloc(sizeof(struct big));
> > memset(&big_thing, 0, sizeof(struct big));

>
> Is that correct?
>
> I believe it should be:
> memset(big_thing, 0, sizeof *big_thing);
> or
> memset(big_thing, 0, sizeof(struct big));


You're right. I think we got there in the end

 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Can *common* struct-members of 2 different struct-types, that are thesame for the first common members, be accessed via pointer cast to either struct-type? John Reye C Programming 28 05-08-2012 12:24 AM
Allocating memory to pass back via ctypes callback function Scott Python 1 06-19-2009 11:14 AM
Allocating vector of strings seem to crash. Allocating array ofstrings seems to be ok . Rakesh Kumar C++ 5 12-21-2007 10:42 AM
passing pointer->struct->pointer->struct to function. .. ?? beetle C Programming 2 01-25-2005 06:08 PM
Access from function in struct (pointer to function) to other items in the struct (advanced) Ole C Programming 4 10-26-2004 09:43 PM



Advertisments