mckeeman@wanginst.EDU (William McKeeman) (05/12/87)
<762@mcgill-vision.UUCP> mouse@mcgill-vision.UUCP (der Mouse) writes: >Does this mean that after > >extern char _ctypes_[]; >#define _ctypes (_ctypes_+1) /* so _ctypes[EOF] is ok */ > >the compiler is not permitted to change _ctypes['x'] into _ctypes_['y'] >because (_ctypes_+1)['x'] <-> *((_ctypes_+1)+'x') cannot be transformed >into *(_ctypes_+(1+'x')) <-> _ctypes_[1+'x']? > Thanks for the nice example. My reading of x3j11 from a compiler writers' viewpoint is given below. I substituted c for _ctypes, ct for _ctypes_. There is an unstated assumption in the example that sizeof(char*)==1. extern char ct[]; #define c (ct+1) For the (optimizing) transformations below: c['x'] -> (ct+1)['x'] #define substitution -> *((ct+1)+'x') def of [] -> *(ct+(1+'x')) associative + -> ct[1+'x'] def of [] -> ct['y'] constant folding The type arithmetic here is: (no type yet) -> (char*+int)[] #define substitution -> ((char*+int)+int)* def of [] -> (char*+(int+int))* ! see below -> (char*)[] def of [] -> (char*)[] ! In the abstract machine this transformation is disallowed. This forces the compiler writer back on the "as if" terminology of x3j11. If the actual code has the same as the effect as the abstract machine, then the transformation is allowed. This example hides the possibility of overflow in the (int+int) computation (suppose it had been c[v+'x'] <-> ct[v+'y'] that was being discussed). I do not know what compiler writers will do about this. Reading x3j11 to this level of detail becomes counter productive since clever people like der mouse come up with disturbing counter examples to otherwise reasonable optimizations. What you can be sure of is that different implmentors are going to do different things when the dark corners of the standard are in question. -- W. M. McKeeman mckeeman@WangInst Wang Institute decvax!wanginst!mckeeman Tyngsboro MA 01879