I've been trying to swallow this entire thread, but I'm still not sure
about everything, another problem I have is that I spent today trying
to find answers and pretty much forgot the key questions, but I think
this is close enough to what I was wondering:
"An lvalue is an expression which potentially designates an object." -
This is the definition I got the impression of being right, and the
definition I used in my head when writing this.
About evaluation of lvalue...
If evaluation is a runtime thing and the offset of the variable who's
address is being fetched is known, does the lvalue evaluate then?
If the result of evaluating the expression is an lvalue, then the
expression must be evaluated or you don't have an lvalue. lvalues
themselves do not necessarily cause an evaluation. But if the value
of the object the lvalue designates is needed, then evaluating the
lvalue produces that value.
What offset are you referring to that you think makes a difference?
Take this for example (which is probably containts no-op's):
"*&i"
There is a special exception for the *& construct. Neither operation
is performed.
Here the compiler most likley knows i's offset, so maybe its -8 and
the compiler knows the type is "int", so it knows to start reading the
objects value at the address-offset -8 and to read sizeof(int) bytes.
Evaluation of this expression, even without the exception, need not
require accessing any of the bytes in i (such as when the expression
is on the left of the assignment operator or the operand of the sizeof
operator). On those occasions when the value of i is required, the
compiler does not access i but rather generates code so that when the
evaluation occurs during execution the bytes are accessed.
Then what is the evaluation? Its not a runtime thing here right? Is
While constant expressions may be evaluated during compile time (i =
5+1; need not have an add in the code resulting from this statement),
the compiler is under no obligation to do so. In the more general
case, evaluation is usually a "runtime thing."
the evaluation the code it gets compiled into? If an lvalue already
You want to try rephrasing that sentence into something that more
clearly conveys you concern.
identifies an object, why evaluate it? If the compiler does not know
Because the value of the object may not be known until execution.
what object the lvalue identifies, why is it said to identify an
object? Because it *does* in C? That is, in case of indirection... you
Why do you think they are called "variables"?
give it an address (or address to be) and the lvalue identifies an
object with that address and a type?
The compiler has no way of knowing what the actual address of an
object will be at execution time. What it does do is generate code
that will correctly compute the address when it is needed.
I'm skipping ahead a bit, if an lvalue always evaluates then this is a
question I want to ask:
About the indirection operator...
Basically, depending on context, the indirection operation may
evaluate to one of two different things, acctually, it always have to
evaluate to identify an object, if used where an lvalue is required,
it stops there, the evaluation is done, however when appearing in a
context that does not require an lvalue, the object identified will
have its value fetched, this means the expression evaluates to an
rvalue
Not always. x = sizeof (*y); will not fetch the value of y or the
value of the object y points to. In fact, the code is legal even if
the value of y or the value of *y is indeterminate.
Unless you are writing a compiler, you are drilling way too deep.