eru@tnvsu1.tele.nokia.fi (Erkki Ruohtula) (10/22/90)
The standard says that "sizeof something_of_array_type" gives the size of the array, not that of the pointer to the first element. But when does the "arrayness" disappear in the conversion to pointer? What should "sizeof (struct_pointer->field_of_array_type)" be? Do the parentheses affect the interpretation? There is a compiler that gives the pointer size in the last example, and I am wondering, whether or not this is a bug. -- Erkki Ruohtula / Nokia Telecommunications eru@tele.nokia.fi / P.O. Box 33 SF-02601 Espoo, Finland Disclaimer: These are my private opinions and do not represent the position of Nokia Telecommunications.
rex@aussie.UUCP (Rex Jaeschke) (10/23/90)
> (Erkki Ruohtula) writes: > The standard says that "sizeof something_of_array_type" gives the size of the > array, not that of the pointer to the first element. But when does the > "arrayness" disappear in the conversion to pointer? What should > "sizeof (struct_pointer->field_of_array_type)" be? Do the parentheses affect > the interpretation? In C, an expression that designates an array is converted to a pointer to the first element except when it isn't. Very clear, right? Well, there are only 3 situations where the conversion DOES NOT take place. They are, when the array designating expression is the operand of sizeof or & (remember that ANSI C allows you to take the address of an lvalue array expression), and in a special case of initialization. An example of the latter case, char *pc = "abcd"; the expression "abcd" designates an array of 5 chars and this expression IS converted to a char *. However, in the case of char c[] = "abcd"; the `expression' "abcd" is treated as short-hand notation for {'a', 'b', 'c', 'd', '\0'} and there is NO conversion. In the case of sizeof (struct_pointer->field_of_array_type) the operand still has array type so there's no conversion. The parens are redundant and have no effect. Now something not well understood is that conversions of arrays to pointers is ONLY defined for array expressions that ARE lvalues. The semantics when they are not lvalues is undefined. For example, given struct tag { char c[5]; }; struct tag f(void); what happens with f().c? f returns a struct by value and c is an array member of that structure. However, f() is NOT an lvalue which means that f().c is NOT an lvalue and so it is undefined as to what happens. Certainly you cannot rely on the array/pointer conversion. This is the only place I've been able to come up with an array expression having these properties. (g()->c is not a problem since g()->c can be an lvalue even if g() is not.) In a related situation, given void f(void), what is sizeof(f)? I've had several compilers convert the function designating expression f to a pointer to function and therefore producing an answer. ANSI C, however, says (and K&R implies) this is incorrect and that there is no conversion done making the construct invalid. Why? Because sizeof can only be applied to objects having completed type and a function is not an object. Also, sizeof(f) is equivalent to sizeof(void (void)) and the latter clearly is erroneous. Rex ---------------------------------------------------------------------------- Rex Jaeschke | Journal of C Language Translation | C Users Journal (703) 860-0091 | 2051 Swans Neck Way | DEC PROFESSIONAL uunet!aussie!rex | Reston, Virginia 22091, USA | Programmers Journal ---------------------------------------------------------------------------- Convener of the Numerical C Extensions Group (NCEG) ----------------------------------------------------------------------------
gwyn@smoke.BRL.MIL (Doug Gwyn) (10/24/90)
In article <ERU.90Oct22103249@tnvsu1.tele.nokia.fi> eru@tnvsu1.tele.nokia.fi (Erkki Ruohtula) writes: >What should "sizeof (struct_pointer->field_of_array_type)" be? >Do the parentheses affect the interpretation? >There is a compiler that gives the pointer size in the last example, and I am >wondering, whether or not this is a bug. Yes, at least it's not standard conforming. Section 3.3.1 says that the type and value of a parenthesized expression are identical to those of the unparenthesized expression. The three paragraphs in 3.2.2.1 concerning type conversion in certain contexts clearly could not apply, as is particularly evident for a parenthesized lvalue, without contradicting 3.3.1. Since this is a case where naive reading of the standard could produce a contradiction, feel free to send in an official request to X3 for an interpretation ruling on this point.
darcy@druid.uucp (D'Arcy J.M. Cain) (10/24/90)
In article <ERU.90Oct22103249@tnvsu1.tele.nokia.fi> eru@tnvsu1.tele.nokia.fi (Erkki Ruohtula) writes: >The standard says that "sizeof something_of_array_type" gives the size of the >array, not that of the pointer to the first element. But when does the >"arrayness" disappear in the conversion to pointer? What should >"sizeof (struct_pointer->field_of_array_type)" be? Do the parentheses affect >the interpretation? > I assume you mean something like this: #include <stdio.h> struct S { char a[32]; } s; int main(void) { struct S *ps = &s; printf("%d - %d - %d\n", sizeof(ps->a), sizeof(s), sizeof(ps)); return(0); } Compiled & run on ESIX 3.2 Rel D and GNU C 1.36. The result I get is "32 - 32 - 4" which is exactly what I expected on my system. >There is a compiler that gives the pointer size in the last example, and I am >wondering, whether or not this is a bug. My vote is for bug if you get 4 as the first number with the above code. The expression ps->a is not a pointer to anything. It is an array which is part of a structure pointed to by ps. Remember that ps->a means (*ps).a which is perhaps more obvious. The parens *are* necessary because ps is dereferenced first and so the expression reduces to <some_structure_of_type_S>.a which is obviously an array. -- D'Arcy J.M. Cain (darcy@druid) | D'Arcy Cain Consulting | I support gun control. West Hill, Ontario, Canada | Let's start with the government! + 416 281 6094 |