Solve Segmentation Fault: Destroy Planetary System "Solid

  • MHB
  • Thread starter mathmari
  • Start date
  • Tags
    Fault
In summary: Wondering)In summary, the conversation is about writing a function for the destruction of a planetary system and troubleshooting a segmentation fault in the code. The expert suggests using assert commands before the problematic code and adding fflush(NULL) after printf to check for any issues. The use of a debugger like gdb is also suggested to further analyze and debug the code.
  • #1
mathmari
Gold Member
MHB
5,049
7
Hey! :eek:

I have to write a function for the destruction of the planetary system "solid".
With the destruction of the planetary system, the asteroids where the gap between this one and the object, is at least "gap" will also be destructed. (so, they have to be deleted) The asteroids for which the gap is greater are converted to free-floating planets consisting a new collection of free-floating planets (ffplan_t). This new collection should be added to the array of the free-floating planets of the star system to which the planetary system, that is destructed, belonged. The identifier "fp" of the new collection is the identifier of the planetary system that is destructed. The list of the free-floating planets that corresponds to the new collection should be sorted as for the field "as" of the asteroids that are contained. The destructed planetary system should be deleted from the list of planetary systems of the star system to which it belonged.

The function should print the following:

Planetary system: < solid >_1 , < solid >_2 , ... , < solid >_n

Free-floating planetsA: < fp > _1 , < fp >_2 , ... , < fp >_n

Free-floating planets: < FFP >_1 , < FFP >_2 , ... , < FFP >_n
< solid >_i is the identifier of the ith planetary system of the Solar System to which the deleted planetary system belonged.

< fp >_i is the identifier of the ith collection of the free-floating planets in the array of the free-floating planets of the Solar System to which the deleted planetary system belonged.

< FFP >_i is the identifier of the ith free-floating planet in the list of the free-floating planets in the new collection of the free-floating planets of the Solar System to which the deleted planetary system belonged. I have done the following:

Code:
int ffplanpos=0;

int destruction(int solid, int gap){
	int i, j;
	int sum=0;
	plansys_t *p=StarS[0].plasy;
	for(i=0; i<Sfreep; i++){
		p=StarS[i].plasy;
		while (p != NULL && p->solid != solid){
			p=p->next;
			j=i;
		}
	}
	if(p == NULL){
		printf("The planetary system with identifier %d couldn't be found\n", solid);
		exit;
	}
	asteroid_t *f=p->asteroids;
	while(sum<gap){
		sum=sum+f->gap;
		f=f->next;
		DELETE(f->prev, f->prev->as);
	}
	
	StarS[j].ffplan[ffplanpos].fp=solid;
	ffplanpos++;
	
	asteroid_t *planf = calloc(1, sizeof(asteroid_t));
	planf->as=f->as;
	planf->gap=0;
	planf->next=NULL;
	planf->prev=NULL;
	asteroid_t *K=StarS[j].ffplan[ffplanpos].ff;
	f=f->next;
	while(f != NULL){
		if (K == NULL) {
        	K = planf;
        } else {
        	asteroid_t *last = K;
        	while (last->next != NULL) {
        		last = last->next;
        	}
        	last->next = planf;
       	}     
		f=f->next;
	}      
	
	
	printf("\n\nPlanet Systems = ");
	
	while(StarS[j].plasy != NULL){
		printf(" %d ", StarS[j].plasy->solid);
		StarS[j].plasy=StarS[j].plasy->next;
	}
	
	printf("\n\nFree-floatingM = ");
	
	for(i=0; i<max; i++){
		printf(" %d ", StarS[j].ffplan[i].fp);
	}
	
	printf("\n\nFree-floating planets = ");
	
	for(i=0; i<max; i++){
		while(StarS[j].ffplan[i].ff != NULL){
			printf(" %d ", StarS[j].ffplan[i].ff->as);
			StarS[j].ffplan[i].ff=StarS[j].ffplan[i].ff->next;
		}
	}
	
	return 0;
	
}

When I run this function, I get a segmentation fault.

What mistake could I have done?? (Wondering)
 
Technology news on Phys.org
  • #2
I made some parts of the function into comments and I found that the segmentation fault occurs because of the following part:

Code:
for(i=0; i<ffplanpos; i++){
		while(StarS[j].ffplan[i].ff != NULL){
			printf(" %d ", StarS[j].ffplan[i].ff->as);
			StarS[j].ffplan[i].ff=StarS[j].ffplan[i].ff->next;
		}
	}

Could you tell me what I have done wrong?? (Wondering)
 
  • #3
Hey! (Smile)

mathmari said:
I made some parts of the function into comments and I found that the segmentation fault occurs because of the following part:

Code:
for(i=0; i<ffplanpos; i++){
		while(StarS[j].ffplan[i].ff != NULL){
			printf(" %d ", StarS[j].ffplan[i].ff->as);
			StarS[j].ffplan[i].ff=StarS[j].ffplan[i].ff->next;
		}
	}

Could you tell me what I have done wrong?? (Wondering)

How can you tell that all indices are within their respective ranges? (Wondering)

Does this code printf anything before it crashes? (Wondering)

Which compiler do you use to compile this? (Wondering)
Are you already familiar with debuggers?
And with core dumps?
 
  • #4
I like Serena said:
How can you tell that all indices are within their respective ranges? (Wondering)

ffplanpos is in its range, because of the following:

Code:
if(ffplanpos<max){
		StarS[j].ffplan[ffplanpos].fp=solid;
		ffplanpos++;
	}
	
	if(ffplanpos>=max){
		return -1;
	}

right?? (Wondering)

What else do I have to check if it is in its range?? (Wondering)
I like Serena said:
Does this code printf anything before it crashes? (Wondering)

When the for-loop is not into comments, it doesn't print anything before it crashes.
I like Serena said:
Which compiler do you use to compile this? (Wondering)
Are you already familiar with debuggers?
And with core dumps?

I use a Cygwin Compiler.

No, I am not familiar with debuggers and core dumps... (Sweating)
 
  • #5
mathmari said:
ffplanpos is in its range, because of the following:

Code:
if(ffplanpos<max){
		StarS[j].ffplan[ffplanpos].fp=solid;
		ffplanpos++;
	}
	
	if(ffplanpos>=max){
		return -1;
	}

right?? (Wondering)

What else do I have to check if it is in its range?? (Wondering)

Should be, but just to be sure, I would add the following before this code:
[m]assert(j >= 0);
assert(j < N);
assert(ffplanpos >= 0);
assert(ffplanpos < max);[/m]
(Nerd)
When the for-loop is not into comments, it doesn't print anything before it crashes.

And what if you add [m]fflush(NULL)[/m] immediately after the printf? (Wondering)
I use a Cygwin Compiler.

No, I am not familiar with debuggers and core dumps... (Sweating)

Does that mean you use [m]gcc[/m] to compile?
If so, can you also use [m]gdb[/m]? (Wondering)
If it's not there, perhaps you can add it to the cygwin installation. (Thinking)
 
  • #6
I like Serena said:
Should be, but just to be sure, I would add the following before this code:
[m]assert(j >= 0);
assert(j < N);
assert(ffplanpos >= 0);
assert(ffplanpos < max);[/m]
(Nerd)

Because my compiler doesn't accept these commands, I wrote the following:

Code:
if(j >= 0) printf("j>=0 OK!\n");
if(j < N) printf("j<N OK!\n");
if(ffplanpos >= 0) printf("ffplanpos>=0 OK!\n");
if(ffplanpos < max) printf("ffplanpos<max OK!\n");

When I run it I get:
[m]j>=0 OK!
ffplanpos>=0 OK!
ffplanpos<max OK![/m]

That means that [m]j[/m] is out of its range, right?? (Wondering)

Why does this occur??

We found [m]j[/m] as followed:

Code:
for(i=0; i<Sfreep; i++){
		p=StarS[i].plasy;
		while (p != NULL && p->solid != solid){
			p=p->next;
			j=i;
		}
	}

and [m]Sfreep[/m] was checked if it is in its range in an other function

Code:
if(Sfreep<N){
        	// Add a star system to the the array of stars
        	starsystem = &StarS[Sfreep];
        	Sfreep++;
		}
		
		if(Sfreep>=N){
			return -1;
		}
(Wondering)
I like Serena said:
And what if you add [m]fflush(NULL)[/m] immediately after the printf? (Wondering)

Do you mean:

Code:
for(i=0; i<ffplanpos; i++){
		while(StarS[j].ffplan[i].ff != NULL){
			printf(" %d ", StarS[j].ffplan[i].ff->as);
			fflush(NULL);
			StarS[j].ffplan[i].ff=StarS[j].ffplan[i].ff->next;
		}
	}

?? (Wondering)

I run the program, but nothing changes.

What should this command do?? (Wondering)

I like Serena said:
Does that mean you use [m]gcc[/m] to compile?
If so, can you also use [m]gdb[/m]? (Wondering)
If it's not there, perhaps you can add it to the cygwin installation. (Thinking)

Yes, I use [m]gcc[/m] to compile.

How can I use [m]gdb[/m]?? [m]gdb name.c[/m] ?? (Wondering)
 
  • #7
mathmari said:
Because my compiler doesn't accept these commands

Well, you have to add [m]#include <assert.h>[/m] to make it compile. (Nerd)
That means that [m]j[/m] is out of its range, right?? (Wondering)

It seems that way and it explains the segmentation fault. (Worried)
We found [m]j[/m] as followed:

Code:
for(i=0; i<Sfreep; i++){
		p=StarS[i].plasy;
		while (p != NULL && p->solid != solid){
			p=p->next;
			j=i;
		}
	}

and [m]Sfreep[/m] was checked if it is in its range in an other function

What if the system wasn't found for some reason? (Wondering)
What should this command do?? (Wondering)

The output of printf is buffered.
And when a program crashes, some of the output will never show up.
The call to [m]fflush(NULL)[/m] ensures that anything that might have been buffered is flushed so you can see it on the screen. (Nerd)

Yes, I use [m]gcc[/m] to compile.

How can I use [m]gdb[/m]?? [m]gdb name.c[/m] ?? (Wondering)

If you use gcc like:
[m]$ gcc -g program.c -o program[/m]

then afterwards you can use gdb like:
[m]$ gdb program
(gdb) run
<crash>
(gdb) bt[/m]

The last command "bt" generates a so called backtrace that shows where and how the program crashed. (Nerd)
 
  • #8
I like Serena said:
Well, you have to add [m]#include <assert.h>[/m] to make it compile. (Nerd)

Ahaa... Ok! (Malthe)
I like Serena said:
What if the system wasn't found for some reason? (Wondering)

Why can this occur?? Isn't this case when [m]if(p == NULL)[/m] at the following part?? (Wondering)

Code:
for(i=0; i<Sfreep; i++){
		p=StarS[i].plasy;
		while (p != NULL && p->solid != solid){
			p=p->next;
			j=i;
		}
	}
	if(p == NULL){
		printf("The planetary system with identifier %d couldn't be found\n", solid);
		exit;
	}
I like Serena said:
If you use gcc like:
[m]$ gcc -g program.c -o program[/m]

then afterwards you can use gdb like:
[m]$ gdb program
(gdb) run
<crash>
(gdb) bt[/m]

The last command "bt" generates a so called backtrace that shows where and how the program crashed. (Nerd)

When I run the program using [m]gdb[/m] it prints infinitely [m]2[/m].
 
  • #9
mathmari said:
Why can this occur?? Isn't this case when [m]if(p == NULL)[/m] at the following part?? (Wondering)

Code:
for(i=0; i<Sfreep; i++){
		p=StarS[i].plasy;
		while (p != NULL && p->solid != solid){
			p=p->next;
			j=i;
		}
	}
	if(p == NULL){
		printf("The planetary system with identifier %d couldn't be found\n", solid);
		exit;
	}

Let's take a closer look.

If each StarS has a non-NULL plasy, then j gets a new value every time, ending in Sfreep.
Is that intended? (Wondering)

After the for-loop, p has the value of the last iteration, which is StarS[Sfreep].plasy.
Likely, that is NULL, in which case we get the printf followed by exit.
However, exit is a function.
Writing it without parentheses (), will have no effect, and the program will continue. :eek:

I suggest to compile with something like:
[m]gcc -g -ansi -pedantic -Wall program.c -o program[/m]

Then you'll get more information, including a message that the use of [m]exit;[/m] has no effect.
When I run the program using [m]gdb[/m] it prints infinitely [m]2[/m].

Aha! (Smile)
So you do have gdb, and it does do something (if not what you wanted). (Happy)

The fact that it behaves differently, suggests you have some uninitialized data somewhere that influences how the program runs. (Worried)

You might dig a little deeper, and try to figure out what the program does.
You can do that with:
[m]$ gdb program
(gdb) b main
(gdb) run
(gdb) next
(gdb) next[/m]
It will show you step by step what your program does.

Here is for instance a quick reference to gdb.
The first 2 sections should be enough for your purposes at this time. (Nerd)
 
  • #10
I like Serena said:
I suggest to compile with something like:
[m]gcc -g -ansi -pedantic -Wall program.c -o program[/m]

Then you'll get more information, including a message that the use of [m]exit;[/m] has no effect.

I get the following:

[m]
stars.c: In function `Constitution':
stars.c:86: error: parse error before '/' token
stars.c:95: error: parse error before '/' token
stars.c:102: error: parse error before '/' token
stars.c: In function `Beginning':
stars.c:110: error: parse error before '/' token
stars.c:113: error: `plansystem' undeclared (first use in this function)
stars.c:113: error: (Each undeclared identifier is reported only once
stars.c:113: error: for each function it appears in.)
stars.c:120: error: parse error before '/' token
stars.c:123: error: parse error before '/' token
stars.c:125: error: `last' undeclared (first use in this function)
stars.c:128: error: parse error before '/' token
stars.c: In function `asteroid_constitution':
stars.c:143: warning: ISO C90 forbids mixed declarations and code
stars.c: In function `destruction':
stars.c:245: warning: ISO C90 forbids mixed declarations and code
stars.c:268: warning: ISO C90 forbids mixed declarations and code
stars.c:273: warning: ISO C90 forbids mixed declarations and code
stars.c:308: error: parse error before '/' token
stars.c:243: warning: statement with no effect
stars.c: In function `asteroid_freefloating_boom':
stars.c:389: warning: ISO C90 forbids mixed declarations and code
stars.c: In function `Search_asteroid':
stars.c:416: warning: ISO C90 forbids mixed declarations and code
stars.c: In function `get_asteroids':
stars.c:442: warning: ISO C90 forbids mixed declarations and code
stars.c: In function `type_planetary':
stars.c:476: warning: ISO C90 forbids mixed declarations and code
stars.c: In function `type_ffcol':
stars.c:504: warning: ISO C90 forbids mixed declarations and code
stars.c:507: warning: too few arguments for format
stars.c:507: warning: too few arguments for format
stars.c:510: warning: too few arguments for format
stars.c:510: warning: too few arguments for format
stars.c:513: warning: too few arguments for format
stars.c:513: warning: too few arguments for format
stars.c:516: warning: too few arguments for format
stars.c:516: warning: too few arguments for format
stars.c: In function `freefloating_collection_boom':
stars.c:575: warning: ISO C90 forbids mixed declarations and code
stars.c:612: error: parse error before '/' token
stars.c:614: error: missing terminating " character
stars.c: In function `main':
stars.c:680: warning: ISO C90 forbids mixed declarations and code
stars.c:692: warning: ISO C90 forbids mixed declarations and code
stars.c:738: warning: ISO C90 forbids mixed declarations and code
[/m]

(Sweating)(Wondering)
I like Serena said:
Aha! (Smile)
So you do have gdb, and it does do something (if not what you wanted). (Happy)

The fact that it behaves differently, suggests you have some uninitialized data somewhere that influences how the program runs. (Worried)

You might dig a little deeper, and try to figure out what the program does.
You can do that with:
[m]$ gdb program
(gdb) b main
(gdb) run
(gdb) next
(gdb) next[/m]
It will show you step by step what your program does.

Here is for instance a quick reference to gdb.
The first 2 sections should be enough for your purposes at this time. (Nerd)
[m]b main[/m] :
[m]Breakpoint 1 at 0x40166c: file stars.c, line 266.[/m]

[m]run[/m] :
...
[m]Breakpoint 1, main() at stars.c, line 266.[/m]
[m]warning: Source file is more recent than executable.[/m]
[m]266[/m]

[m]next[/m] :
[m]274[/m] [m]f=f->next;[/m]

[m]next[/m] :
[m]275[/m] [m]while(f != NULL){[/m]What does this mean?? (Wondering)
 
  • #11
mathmari said:
I get the following:

[m]
stars.c: In function `Constitution':
stars.c:86: error: parse error before '/' token
stars.c:95: error: parse error before '/' token
stars.c:102: error: parse error before '/' token
stars.c: In function `Beginning':
stars.c:110: error: parse error before '/' token
stars.c:113: error: `plansystem' undeclared (first use in this function)
stars.c:113: error: (Each undeclared identifier is reported only once
stars.c:113: error: for each function it appears in.)
stars.c:120: error: parse error before '/' token
stars.c:123: error: parse error before '/' token
stars.c:125: error: `last' undeclared (first use in this function)
stars.c:128: error: parse error before '/' token
stars.c: In function `asteroid_constitution':
stars.c:143: warning: ISO C90 forbids mixed declarations and code
stars.c: In function `destruction':
stars.c:245: warning: ISO C90 forbids mixed declarations and code
stars.c:268: warning: ISO C90 forbids mixed declarations and code
stars.c:273: warning: ISO C90 forbids mixed declarations and code
stars.c:308: error: parse error before '/' token
stars.c:243: warning: statement with no effect
stars.c: In function `asteroid_freefloating_boom':
stars.c:389: warning: ISO C90 forbids mixed declarations and code
stars.c: In function `Search_asteroid':
stars.c:416: warning: ISO C90 forbids mixed declarations and code
stars.c: In function `get_asteroids':
stars.c:442: warning: ISO C90 forbids mixed declarations and code
stars.c: In function `type_planetary':
stars.c:476: warning: ISO C90 forbids mixed declarations and code
stars.c: In function `type_ffcol':
stars.c:504: warning: ISO C90 forbids mixed declarations and code
stars.c:507: warning: too few arguments for format
stars.c:507: warning: too few arguments for format
stars.c:510: warning: too few arguments for format
stars.c:510: warning: too few arguments for format
stars.c:513: warning: too few arguments for format
stars.c:513: warning: too few arguments for format
stars.c:516: warning: too few arguments for format
stars.c:516: warning: too few arguments for format
stars.c: In function `freefloating_collection_boom':
stars.c:575: warning: ISO C90 forbids mixed declarations and code
stars.c:612: error: parse error before '/' token
stars.c:614: error: missing terminating " character
stars.c: In function `main':
stars.c:680: warning: ISO C90 forbids mixed declarations and code
stars.c:692: warning: ISO C90 forbids mixed declarations and code
stars.c:738: warning: ISO C90 forbids mixed declarations and code
[/m]

(Sweating)(Wondering)

As you can see, there are a couple of things not quite right.
Most, but not all, will go away when you:
  • Change comments like "// comment" to "/* comment */".
  • Do all declarations of variables before normal statements.
After that we'll have to see what's left. (Sweating)
[m]b main[/m] :
[m]Breakpoint 1 at 0x40166c: file stars.c, line 266.[/m]

[m]run[/m] :
...
[m]Breakpoint 1, main() at stars.c, line 266.[/m]
[m]warning: Source file is more recent than executable.[/m]

This means that you changed stars.c after compiling it for the last time. (Worried)
[m]266[/m]

[m]next[/m] :
[m]274[/m] [m]f=f->next;[/m]

[m]next[/m] :
[m]275[/m] [m]while(f != NULL){[/m]

This means you're "stepping" through the code.
At each time, you can see what the program is doing, and you can inspect the value of the variables.

What you could do next, is:
[m](gdb) b <line number just before the segmentation fault>[/m]
[m](gdb) c[/m]
Then perhaps use:
[m](gdb) n[/m]
to step until the point where you think it's going wrong.
Use for instance:
[m](gdb) p j[/m]
to print the contents of variable j, so you can see what it is.
(Wasntme)
 
  • #12
I like Serena said:
As you can see, there are a couple of things not quite right.
Most, but not all, will go away when you:
  • Change comments like "// comment" to "/* comment */".
  • Do all declarations of variables before normal statements.
After that we'll have to see what's left. (Sweating)

Now it is:

[m]stars.c: In function 'destruction':
stars.c:246: warning: statementwith no effect[/m]

So, should I replace [m]exit;[/m] with [m]return -1;[/m] ??(Wondering)
 
  • #13
mathmari said:
Now it is:

[m]stars.c: In function 'destruction':
stars.c:246: warning: statementwith no effect[/m]

So, should I replace [m]exit;[/m] with [m]return -1;[/m] ??(Wondering)

If you use exit, it should be [m]exit(EXIT_FAILURE);[/m].
You can also use [m]return -1;[/m]. (Mmm)
 
  • #14
I like Serena said:
If you use exit, it should be [m]exit(EXIT_FAILURE);[/m].
You can also use [m]return -1;[/m]. (Mmm)

Ok! (Smile)Now, I made the for-loop into comments and I tried to print the following:

[m]printf("\n\n %d ", StarS[j].ffplan[ffplanpos].ff->as);[/m]

but I get a segmentation fault.

Is there maybe an error at [m]StarS[j].ffplan[ffplanpos].ff->as[/m] ?? (Wondering)Also I printed [m]j[/m] and it is [m]0[/m]. So, it is not out of its range, or not?? (Wondering)
 
  • #15
mathmari said:
Is there maybe an error at [m]StarS[j].ffplan[ffplanpos].ff->as[/m] ?? (Wondering)

Is it maybe not defined??

Code:
int ffplanpos=0;
int destruction(int solid, int gap){
	int i, j;
	int sum=0;
	asteroid_t *planf = calloc(1, sizeof(asteroid_t));
	asteroid_t *K=NULL;
	asteroid_t *f=NULL;
	plansys_t *p=StarS[0].plasy;
	for(i=0; i<Sfreep; i++){
		p=StarS[i].plasy;
		while (p != NULL && p->solid != solid){
			p=p->next;
			j=i;
		}
	}
	if(p == NULL){
		printf("The planetary system with identifier %d couldn't be found\n", solid);
		return -1;
	}
	f=p->asteroids;
	while(sum<gap){
		sum=sum+f->gap;
		f=f->next;
		DELETE(f->prev, f->prev->as);
	}
	

	if(ffplanpos<max){
		StarS[j].ffplan[ffplanpos].fp=solid;
		ffplanpos++;
	}
	
	if(ffplanpos>=max){
		return -1;
	}
	
	planf->as=f->as;
	planf->gap=0;
	planf->next=NULL;
	planf->prev=NULL;
	
	K=StarS[j].ffplan[ffplanpos].ff;
	
	f=f->next;
	while(f != NULL){
		if (K == NULL) {
        	K = planf;
        } else {
        	asteroid_t *last = K;
        	while (last->next != NULL) {
        		last = last->next;
        	}
        	last->next = planf;
       	}     
		f=f->next;
	}     
	
	
	printf("\n\nPlanet Systems = ");
	
	while(StarS[j].plasy != NULL){
		printf(" %d ", StarS[j].plasy->solid);
		StarS[j].plasy=StarS[j].plasy->next;
	}
	
	printf("\n\nFree-floatingM = ");
	
	for(i=0; i<ffplanpos; i++){
		printf(" %d ", StarS[j].ffplan[i].fp);
	}
	
	printf("\n\nFree-floating planets = ");

	for(i=0; i<ffplanpos; i++){
		while(StarS[j].ffplan[i].ff != NULL){
			printf(" %d ", StarS[j].ffplan[i].ff->as);
			StarS[j].ffplan[i].ff=StarS[j].ffplan[i].ff->next;
		}
	}
	
	return 0;
	
}

(Wondering)
 
  • #16
mathmari said:
Ok! (Smile)Now, I made the for-loop into comments and I tried to print the following:

[m]printf("\n\n %d ", StarS[j].ffplan[ffplanpos].ff->as);[/m]

but I get a segmentation fault.

Is there maybe an error at [m]StarS[j].ffplan[ffplanpos].ff->as[/m] ?? (Wondering)Also I printed [m]j[/m] and it is [m]0[/m]. So, it is not out of its range, or not?? (Wondering)

Then there is only one possibility left. ff is NULL or does not point to valid memory.
What do you get if you printf("%p", ff)? (Wondering)
 
  • #17
When I write [m]printf("%p", StarS[j].ffplan[ffplanpos].ff);[/m] I get [m]0x0[/m].

What does this mean?? That it is NULL?? (Wondering)
 
  • #18
mathmari said:
When I write [m]printf("%p", StarS[j].ffplan[ffplanpos].ff);[/m] I get [m]0x0[/m].

What does this mean?? That it is NULL?? (Wondering)

Yep. NULL is defined as 0. (Smirk)
 
  • #19
I like Serena said:
Yep. NULL is defined as 0. (Smirk)

Ok... But why is it NULL?? (Wondering)

Haven't we defined it before?? (Wondering)
 
  • #20
Now I changed something at the code, and when I print [m]printf("%p", StarS[j].ffplan[ffplanpos].ff);[/m] I don't get [m]0x0[/m], but [m]0xb802f0 [/m].

But when I print [m]printf("%p", StarS[j].ffplan[0].ff);[/m] I get [m]0x0[/m].

Why is the position 0 NULL but not the position ffplanpos=1?? (Wondering)
 
  • #21
mathmari said:
Now I changed something at the code, and when I print [m]printf("%p", StarS[j].ffplan[ffplanpos].ff);[/m] I don't get [m]0x0[/m], but [m]0xb802f0 [/m].

But when I print [m]printf("%p", StarS[j].ffplan[0].ff);[/m] I get [m]0x0[/m].

Why is the position 0 NULL but not the position ffplanpos=1?? (Wondering)

What are you doing to initialize [m]StarS[j].ffplan.ff[/m] for various j and i? (Wondering)
 
  • #22
I like Serena said:
What are you doing to initialize [m]StarS[j].ffplan.ff[/m] for various j and i? (Wondering)


In this function there is the following part:

Code:
	if(ffplanpos<max){
		StarS[j].ffplan[ffplanpos].fp=solid;
		ffplanpos++;
	}
	
	if(ffplanpos>=max){
		return -1;
	}
	
	planf->as=f->as;
	planf->gap=0;
	planf->next=NULL;
	planf->prev=NULL;

	f=f->next;
	while(f != NULL){
		if (StarS[j].ffplan[ffplanpos].ff == NULL) {
        	      StarS[j].ffplan[ffplanpos].ff = planf;
                } else {
        	      asteroid_t *last = StarS[j].ffplan[ffplanpos].ff;
        	      while (last->next != NULL) {
        		   last = last->next;
        	      }
        	      last->next = planf;
                }     
		f=f->next;
	}

[m]ffplanpos[/m] is a global variable which is set to 0.
At the first if statement there is only the field [m]fp[/m] ([m]StarS[j].ffplan[ffplanpos].fp=solid;[/m]) and not the field [m]ff[/m] and then we increment [m]ffplanpos[/m]. Now when [m]ffplanpos=1[/m] we have the command [m] StarS[j].ffplan[ffplanpos].ff = planf;[/m]. That means that [m]StarS[j].ffplan[0].ff[/m] is still [m]NULL[/m], right?? (Wondering)
 
  • #23
mathmari said:
In this function there is the following part:

Code:
	if(ffplanpos<max){
		StarS[j].ffplan[ffplanpos].fp=solid;
		ffplanpos++;
	}

[m]ffplanpos[/m] is a global variable which is set to 0.

How can ffplanpos be a global variable if it is used to index the ffplan of a particular StarS[j]? :confused:
It will have the wrong value if we use it for another StarS[j]. (Worried)
 
  • #24
I like Serena said:
How can ffplanpos be a global variable if it is used to index the ffplan of a particular StarS[j]? :confused:
It will have the wrong value if we use it for another StarS[j]. (Worried)

Oh...you're right! (Blush)

Do we have to increment [m]ffplanpos[/m] ??

Code:
if(ffplanpos<max){
		StarS[j].ffplan[ffplanpos].fp=solid;
		ffplanpos++;
	}

(Wondering)
 
  • #25
mathmari said:
Oh...you're right! (Blush)

Do we have to increment [m]ffplanpos[/m] ??

Code:
if(ffplanpos<max){
		StarS[j].ffplan[ffplanpos].fp=solid;
		ffplanpos++;
	}

(Wondering)

Well, we need to know how many free floating planetary systems there are.
But that should be separately for each star system, so we cannot use a single global variable for that. (Thinking)

What is the declaration of [m]starsy_t[/m]? (Wondering)
Does it contain something to track the number of free floating planetary systems for a star system?
Otherwise we need to count them.
 
  • #26
I like Serena said:
Well, we need to know how many free floating planetary systems there are.
But that should be separately for each star system, so we cannot use a single global variable for that. (Thinking)

What is the declaration of [m]starsy_t[/m]? (Wondering)
Does it contain something to track the number of free floating planetary systems for a star system?
Otherwise we need to count them.

The declaration of [m]starsy_t[/m] is the following:

Code:
struct starsy { 
 int ss;               /*Identifier of the star system*/
 plansys_t *plasy;     /*Pointer to the first element in the list of the planetary system */
 ffplan_t ffplan[max];     /*The array of the free-floating planets */
 plansys_t *Sentinel;      /*Pointer to the sentinel node of the list of the planetary system */
};
 
  • #27
mathmari said:
The declaration of [m]starsy_t[/m] is the following:

Code:
struct starsy { 
 int ss;               /*Identifier of the star system*/
 plansys_t *plasy;     /*Pointer to the first element in the list of the planetary system */
 ffplan_t ffplan[max];     /*The array of the free-floating planets */
 plansys_t *Sentinel;      /*Pointer to the sentinel node of the list of the planetary system */
};

There is nothing in there to track the number of ffplan's. (Worried)
That means that if we want to add something in ffplan[], we should iterate over what's already there and find an empty spot, or fail if there are already [m]max[/m] ffplan's. (Thinking)
 
  • #28
I like Serena said:
There is nothing in there to track the number of ffplan's. (Worried)
That means that if we want to add something in ffplan[], we should iterate over what's already there and find an empty spot, or fail if there are already [m]max[/m] ffplan's. (Thinking)

Should it be as followed??

Code:
for(i=0; i<max; i++){
	if(StarS[j].ffplan[i] == INT_MAX){
		ffplanpos=i;
	}
}
	
StarS[j].ffplan[ffplanpos].fp=solid;

(Wondering)
 
  • #29
mathmari said:
Should it be as followed??

Code:
for(i=0; i<max; i++){
	if(StarS[j].ffplan[i] == INT_MAX){
		ffplanpos=i;
	}
}
	
StarS[j].ffplan[ffplanpos].fp=solid;

(Wondering)

That's the right direction. (Smile)
We should still check if can find an empty spot though, and handle it if there are no spots available anymore.
Otherwise we might (and ultimately will) get a segmentation fault. :eek:
 
  • #30
I like Serena said:
That's the right direction. (Smile)
We should still check if can find an empty spot though, and handle it if there are no spots available anymore.
Otherwise we might (and ultimately will) get a segmentation fault. :eek:

Code:
	int ffplanpos=-1;
       
        ...
	

	for(i=0; i<max; i++){
		if(StarS[j].ffplan[i] == INT_MAX){
			ffplanpos=i;
		}
	 }
	
	if(ffplanpos == -1){
		return -1;
	}

Is it better now?? (Wondering)
 
  • #31
mathmari said:
Code:
	int ffplanpos=-1;
       
        ...
	

	for(i=0; i<max; i++){
		if(StarS[j].ffplan[i] == INT_MAX){
			ffplanpos=i;
		}
	 }
	
	if(ffplanpos == -1){
		return -1;
	}

Is it better now?? (Wondering)

Yep! (Smile)
 
  • #32
I like Serena said:
Yep! (Smile)

When I compile it I get an error at the line [m]if(StarS[j].ffplan == INT_MAX){[/m]

[m]error: invalid operands to binary ==[/m]

What does this mean?? (Wondering)
 
  • #33
mathmari said:
When I compile it I get an error at the line [m]if(StarS[j].ffplan == INT_MAX){[/m]

[m]error: invalid operands to binary ==[/m]

What does this mean?? (Wondering)


It means that we cannot compare StarS[j].ffplan to INT_MAX.
Is StarS[j].ffplan an integer?
Or is it perhaps a structure from which we should select a data member? (Wondering)
 
  • #34
I like Serena said:
It means that we cannot compare StarS[j].ffplan to INT_MAX.
Is StarS[j].ffplan an integer?
Or is it perhaps a structure from which we should select a data member? (Wondering)


It is a structure which has the fields [m]fp[/m] (Identifier of the free-floating planet) and [m]ff[/m] (Pointer to the first node of the list of the free-floating planets).

So do we have to write it as followed??

Code:
int ffplanpos=-1;
       
        ...
	

	for(i=0; i<max; i++){
		if(StarS[j].ffplan[i].fp == INT_MAX){
			ffplanpos=i;
		}
	 }
	
	if(ffplanpos == -1){
		return -1;
	}

        StarS[j].ffplan[ffplanpos].fp=solid;

(Wondering)
 
  • #35
mathmari said:
It is a structure which has the fields [m]fp[/m] (Identifier of the free-floating planet) and [m]ff[/m] (Pointer to the first node of the list of the free-floating planets).

So do we have to write it as followed??

Code:
int ffplanpos=-1;
       
        ...
	

	for(i=0; i<max; i++){
		if(StarS[j].ffplan[i].fp == INT_MAX){
			ffplanpos=i;
		}
	 }
	
	if(ffplanpos == -1){
		return -1;
	}

        StarS[j].ffplan[ffplanpos].fp=solid;

(Wondering)

I do not understand yet what [m]ff[/m] should represent, but yes, your code looks correct now. (Smile)
 

Similar threads

Back
Top