Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Dereferencing a pointer in a 'for' loop initializer creates a segmentation fault

I'm having a problem using pointers in a for loop. In my for loop initializer, I dereference an int pointer and give it a value of '0'. When I use that dereferenced pointer in the loop I get a segmentation fault, and I don't understand why. I am using Code::Blocks and the C GNU GCC compiler.

  1. Looking at the watch window I can see that during the for loop the variable has a random number.

  2. It seems that the dereferenced pointer loses scope during the for loop.

The code:

#include <stdio.h>  int main(void) {     int val = 0;     int *p = NULL;     int answer = 0;      p = &val;      *p = 1; // This dereferences and sets to one successfully      for (int i=3, (*p)=0 ; i>=0; i--) // Here *p is a random number     {         printf("do stuff");         (*p) += 1; // Here it causes a segmentation fault     }     answer = *p; } 

I thought that there would be no problems using a pointer the way I am.

like image 475
Mark R Avatar asked Aug 09 '19 13:08

Mark R


People also ask

What happens when you dereference a pointer?

Dereferencing a pointer means getting the value that is stored in the memory location pointed by the pointer. The operator * is used to do this, and is called the dereferencing operator.

Why will a segmentation fault occur when we dereference null?

To quote from Wikipedia: Dereferencing the NULL pointer typically results in an attempted read or write from memory that is not mapped - triggering a segmentation fault or access violation. This may represent itself to the developer as a program crash, or be transformed into an exception that can be caught.

What does the dereference operator (*) do?

In computer programming, a dereference operator, also known as an indirection operator, operates on a pointer variable. It returns the location value, or l-value in memory pointed to by the variable's value.

Why is it called dereferencing a pointer?

Dereferencing means taking away the reference and giving you what it was actually referring to. A pointer to something really means that your pointer variable holds a memory address of something . But the pointer can also be thought of as a reference to something instead.


1 Answers

Take a close look here:

for (int i=3, (*p)=0 ; i>=0; i--) 

In the first part of the for you're defining a new pointer variable named p which shadows the p defined earlier and initializing it to NULL. You then dereference the NULL pointer in the loop which causes the segfault.

You can't have both a variable definition and an assignment to an existing variable together like that, so move the assignment of *p to before the loop:

*p = 0; for (int i=3; i>=0; i--) 

Or you can define i outside of the loop:

int i; for (i=3, (*p)=0 ; i>=0; i--) 

You could squeeze these together by abusing the comma operator:

for (int i=(*p=0,3) ; i>=0; i--) 

Here the assignment to p happens as part of the initializer for i so it doesn't declare a new variable. But I wouldn't recommend this as it would make your code more difficult to read and understand.

like image 175
dbush Avatar answered Oct 16 '22 01:10

dbush