Help with two pointer problems in C.

  • Thread starter Thread starter MorrowUoN
  • Start date Start date
AI Thread Summary
The discussion focuses on two C programming pointer problems. In the first problem, the code sets the value of x to 0x1000 and increments the pointer y to point to the next memory location, resulting in y having the value of 0x1202. The second problem involves an array where a loop modifies its elements, but confusion arises regarding pointer arithmetic and the effect of incrementing pointers. It is clarified that incrementing a pointer moves it to the next element based on the type size, and that pointing one past the end of an array is legal in C. Understanding pointer behavior and operator precedence is crucial for correctly interpreting the code's functionality.
MorrowUoN
Messages
8
Reaction score
0
What is the value of x after the following C code sequence?
Discuss the value of y.

int x = 0x1201, *y;
y = &x;
*y++ = 0x1000;

Analyse the following code and provide the values of the elements of the array x
after the code is executed.
int x[] = {1, 2, 3, 0, 5, 6, 0};
int *px = x;
do
{
*px += *x;
px++;
} while (*px != 0);

Any help is appreciated, thanks.
 
Physics news on Phys.org
These look like homework problems. We need to see your thoughts on what you think the code does before we can help.

For the first problem, you can see that y points to x so ask yourself what happens first the assignment of 0x1000 or the ++ increment of the y integer pointer?

For the second, look at the loop what is it doing? px --> x which means it points to x[0]
 
  • Like
Likes 1 person
For the first question I got:

y=0x1001 and x= 0x1000

My logic for this was y is pointing to the address of x and since y++ is post increment it sets x to 0x1000 and then y increments and becomes 0x1001.Also these questions are from a sample final exam for which we haven't been given the solutions.
 
Last edited:
MorrowUoN said:
I'm confused with the second one since there is no unary operator,causing me to think that array x isn't changed.
I'm not sure if this is the source of confusion, but *x is a pointer, not a unary multiply.
 
MorrowUoN said:
For the first question I got:

y=0x1001 and x= 0x1000

My logic for this was y is pointing to the address of x and since y++ is post increment it sets x to 0x1000 and then y increments and becomes 0x1001.
You got the right value for x, but that was bit lucky. Your logic is incorrect, and your value of y is incorrect.

You appear to have a basic misunderstanding of pointers and the post increment operator.

As a hint, which of the following two expressions is the same as *y++ : *(y++) or (*y)++ ? You may need to consult a C precedence table.

What does *(y++) = 0x1000 do, in detail? How about (*y)++ = 0x1000 ?
 
  • Like
Likes 1 person
D H said:
You got the right value for x, but that was bit lucky. Your logic is incorrect, and your value of y is incorrect.

You appear to have a basic misunderstanding of pointers and the post increment operator.

As a hint, which of the following two expressions is the same as *y++ : *(y++) or (*y)++ ? You may need to consult a C precedence table.

What does *(y++) = 0x1000 do, in detail? How about (*y)++ = 0x1000 ?

I believe this to be correct: *y++ = *(y++)

The precedence table I looked at had ++ above unary *.

I'm having trouble with this *(y++) = 0x1000 due to never seeing anything like it before.

This is what I think it does although I could be wrong.

it sets *y = 0x1000 therefore x=0x1000 and then increments y so y = 0x1201 + 1 = 0x1202 ?
 
MorrowUoN said:
I believe this to be correct: *y++ = *(y++)

The precedence table I looked at had ++ above unary *.
That is the correct interpretation of *y++. So far, so good. In fact, the alternate interpretation (*y)++ = 0x1000 isn't valid code.


I'm having trouble with this *(y++) = 0x1000 due to never seeing anything like it before.

This is what I think it does although I could be wrong.

it sets *y = 0x1000 therefore x=0x1000 and then increments y so y = 0x1201 + 1 = 0x1202 ?
There are two things wrong here. One is the "and then". It's better to look at the post-increment operator as a function that saves the variable value, increments, and returns the saved value. This suggests that y is incremented first rather than your "and then increments y".

An even better way to look at it is that order must not matter. Consider the statement *y++ = *y--; What does this do? The answer is whatever the compiler wants. It would be perfectly valid for the compiler to call the function erase_my_harddrive() in response to this statement.


The second thing that's wrong is your interpretation of what happens to y. y is a pointer. It does not contain 0x1201 initially. It points to a location in memory that contains that value.

What does incrementing a pointer do?
 
So basically after that line y just points to the next available memory location?
 
MorrowUoN said:
So basically after that line y just points to the next available memory location?
It doesn't matter if the location is available or not, it ends up pointing to the next memory location after x, which may or not be "available" (it's possible but unlikely that trying to access the next memory location after x would cause a segmentation fault).
 
  • #10
MorrowUoN said:
So basically after that line y just points to the next available memory location?

It depends on what you mean by the next "available" memory location. Pointer arithmetic, including increment and decrement is scaled by the type of object being pointed to.

What this means is that an expression such as p++ depends on how p was defined. If p is defined as a char *, then incrementing p will result in an address that is one byte higher in memory. If p is defined as an int *, them incrementing p will result in an address four bytes higher in memory.

It's the same with expressions such as p + 1, where again, p is defined as a pointer to some specific type. The value of p + 1 depends on how p was defined. To repeat what I said before, pointer arithmetic is scaled by the type of object being pointed to.
 
  • #11
MorrowUoN said:
So basically after that line y just points to the next available memory location?
It points to "one past the end of x", whatever that happens to be. While it is not legal to access the contents of a "one past the end an array" pointer, it is perfectly legal to set a pointer so that it points to one element past the end of an array. In other words, the statement *y++ = 0x1000; is perfectly legal. Dereferencing y after this statement (e.g., x = *y) is illegal. That belongs to that extremely nasty class of things called undefined behavior. The compiler is free to interpret the second statement of *y++ = 0x1000; x = *y; as a call to erase_my_harddrive().

rcgldr said:
It doesn't matter if the location is available or not, it ends up pointing to the next memory location after x, which may or not be "available" (it's possible but unlikely that trying to access the next memory location after x would cause a segmentation fault).
A segmentation fault in response to *y++ where y points to a valid memory location (e.g., &x) is not possible in a compliant implementation. The standard is very clear on this. Pointing one past the end of an array is a perfectly legal operation.

Aside: C++ depends on this being legal. "One past the end" is effectively what the end() function of a container points to.
 
  • #12
D H said:
A segmentation fault in response to *y++ where y points to a valid memory location (e.g., &x) is not possible in a compliant implementation. The standard is very clear on this. Pointing one past the end of an array is a perfectly legal operation.
I was referring to the case of y = &x; ... y++; x = *y;. In this case y is a pointer to a single integer, not an integer that is part of an array. Depending on memory protection capabilities of a system, it's possible that the memory addresses immediately after x are set to invalid.

A more likely way to produce a fault would be in an embedded environment where instead of x, y was set to be a pointer to a integer that is the last valid address in a range of valid addresses.
 

Similar threads

Replies
17
Views
2K
Replies
2
Views
2K
Replies
23
Views
8K
Replies
3
Views
1K
Replies
2
Views
2K
Back
Top