struct task_struct;

A

Allan Adler

I think this is a C question rather than a Linux question.

I have a copy of Linux Core Kernel Commentary, Scott Maxwell, published
in 1999. On p.110, the source for include/asm-i386/current.h begins

#ifndef _I386_CURRENT_H
#define _I386_CURRENT_H

struct task_struct;

I'm not very good at C, so maybe this is really a dumb question, but it
is my impression that one does not simply write things like

struct task_struct;

I thought structure declarations had to have more in them, e.g. something like:

struct gleep { int gleep_no; char gleep_char;} gleep_instance;

What does it signify just to write "struct task_struct;"?
 
S

Steffen

Hi,

Allan said:
I'm not very good at C, so maybe this is really a dumb question, but it
is my impression that one does not simply write things like

struct task_struct;

I thought structure declarations had to have more in them, e.g. something like:

struct gleep { int gleep_no; char gleep_char;} gleep_instance;

What does it signify just to write "struct task_struct;"?

What you have there is called a "forward declaration".
After having made it, you can use the name task_struct, unless the
compiler needs to know the size of it. For example you can now define
pointers to task_struc.

A forward declaration is necessary when you have two objects that are to
hold pointers to each other. Naively writing

struct A {
B* ptr_to_b;
};

struct B {
A* ptr_to_a;
};

doesn't work, since in the declaration of A the compiler doens't know B
yet. So you put a

struct B;

in front of it.

Steffen
 
K

Kenneth Brody

Allan said:
I think this is a C question rather than a Linux question.

I have a copy of Linux Core Kernel Commentary, Scott Maxwell, published
in 1999. On p.110, the source for include/asm-i386/current.h begins

#ifndef _I386_CURRENT_H
#define _I386_CURRENT_H

struct task_struct;

I'm not very good at C, so maybe this is really a dumb question, but it
is my impression that one does not simply write things like

struct task_struct;

I thought structure declarations had to have more in them, e.g. something like:

struct gleep { int gleep_no; char gleep_char;} gleep_instance;

What does it signify just to write "struct task_struct;"?

It says that you have a struct named "task_struct", but does not define
the structure itself. This will allow you to make reference to the
struct, as long as you don't need to know how it's defined. For example,
you can define a function which gets passed a "struct task_struct *",
or returns such a pointer. (Note that you can define such functions
without the above declaration, but the compiler is probably free to give
a warning that it's not defined/declared.)

The actual definition of the struct is elsewhere.

--
+-------------------------+--------------------+-----------------------------+
| Kenneth J. Brody | www.hvcomputer.com | |
| kenbrody/at\spamcop.net | www.fptech.com | #include <std_disclaimer.h> |
+-------------------------+--------------------+-----------------------------+
Don't e-mail me at: <mailto:[email protected]>
 
I

Irrwahn Grausewitz

What you have there is called a "forward declaration".
After having made it, you can use the name task_struct, unless the
compiler needs to know the size of it. For example you can now define
pointers to task_struc.

A forward declaration is necessary when you have two objects that are to
hold pointers to each other. Naively writing

struct A {
B* ptr_to_b;
};

struct B {
A* ptr_to_a;
};

doesn't work, since in the declaration of A the compiler doens't know B
yet. So you put a

struct B;

in front of it.

And, in order to make it work, you have to write
struct B* ptr_to_b;
and
struct A* ptr_to_a;
respectively in above declarations, since in C the keyword struct,
though introducing a new type, does not automatically generate a
typedef-name for that new type - unlike that other language with a
capital c in its name.

Best regards
 
A

Antonio Contreras

Steffen said:
Hi,



What you have there is called a "forward declaration".
After having made it, you can use the name task_struct, unless the
compiler needs to know the size of it. For example you can now define
pointers to task_struc.

Wouldn't the compiler need to know the size of the struct to be able to
actually decide how to implement a pointer to such a structure (I'm
thinking of alignment needs)?
 
I

Irrwahn Grausewitz

Antonio Contreras said:
Wouldn't the compiler need to know the size of the struct to be able to
actually decide how to implement a pointer to such a structure (I'm
thinking of alignment needs)?

C has what is called "incomplete types". It's perfectly legitimate to
define pointers to incomplete types. If alignment is an issue, the
compiler has to take care of that. For example think about void
pointers: since a pointer to void (an incomplete type that cannot be
completed) can be converted to a pointer to any other object type, it
has to be suitable aligned.

Best regards.
 
K

Kenneth Brody

Antonio said:
Hi,

Allan Adler wrote: [...]
What does it signify just to write "struct task_struct;"?

What you have there is called a "forward declaration".
After having made it, you can use the name task_struct, unless the
compiler needs to know the size of it. For example you can now define
pointers to task_struc.

Wouldn't the compiler need to know the size of the struct to be able to
actually decide how to implement a pointer to such a structure (I'm
thinking of alignment needs)?

Nothing in this code needs to know anything about "mystruct":

typedef struct mystruct MYSTRUCT;
extern int realfunc(MYSTRUCT *,int);

int mywrapper(MYSTRUCT *pt)
{
static int depth = 0;
int retval;

depth++;
retval = realfunc(pt,depth);
depth--;

return(retval);
}

A pointer variable doesn't need to be suitably aligned based on what it
points to. The value of the pointer needs to be aligned. (I hope I've
explained that well.)

So, "struct task_struct *ptask;" doesn't need to know anything about the
struct to be properly handled. It's not until you try to do something
with the pointer (dereference it, increment it, malloc(sizeof(*ptask)),
etc.) does it need to know the complete struct definition.

--
+-------------------------+--------------------+-----------------------------+
| Kenneth J. Brody | www.hvcomputer.com | |
| kenbrody/at\spamcop.net | www.fptech.com | #include <std_disclaimer.h> |
+-------------------------+--------------------+-----------------------------+
Don't e-mail me at: <mailto:[email protected]>
 
K

Keith Thompson

Antonio Contreras said:
Wouldn't the compiler need to know the size of the struct to be able to
actually decide how to implement a pointer to such a structure (I'm
thinking of alignment needs)?

It's possible for different pointer types to have different
representations depending on what they point to. For example, on a
word-addressed machine a byte pointer (char* or void*) might be bigger
than a word pointer (int*). But C specifically requires all struct
pointers to have the same representation, precisely so that incomplete
types will work.
 

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

No members online now.

Forum statistics

Threads
474,169
Messages
2,570,919
Members
47,459
Latest member
Vida00R129

Latest Threads

Top