[comp.lang.fortran] Type punning in C

cik@l.cc.purdue.edu (Herman Rubin) (10/12/89)

In article <1989Oct11.091619.18336@gdt.bath.ac.uk>, exspes@gdr.bath.ac.uk (P E Smee) writes:
> In article <1989Oct10.185851.6490@agate.berkeley.edu> jerry@violet.berkeley.edu ( Jerry Berkman ) writes:
< >
< >Why not use equivalence?
< >	INTEGER I
< >	REAL X, IX
< >	EQUIVALENCE (X,IX)
< >
< >	IX = I
< >The Fortran standard specifies that a REAL and INTEGER occupy the same space.
< >The only problem is this might fool some optimizers.
< >
> Problem is, the Fortran standard *also* says that if your program tries
> to take the value of the variable using a different type than the type you
> used when you last stored into it, your program is invalid.  This is a
> polite way of saying (to the user) 'this trick may not work', and (to the
> compiler writer) 'your optimizer does not have to worry about aliasing
> between variables of different types'.  If the compiler can tell that
> you are going to (e.g.) store an integer into that storage, and then
> read a real, it is under no obligation to make sure that the integer
> value gets stored.
> 
> Fortran equivalence was designed toallow reuse of storage on the early
> small memory machines -- not to allow type punning.  Usually you can
> get away with punning, but it doesn't always work and so is a bad habit.

This is another example of those "gurus" who can not envision an intelligent
user using the machine in an intelligent manner, and prevent that use.  I
have deliberately used "type punning" on various machines, and I consider it
an extremely useful tool.  Now, I do not mind the compiler asking me if I
really wanted to do it, but I object to anyone telling me that I CAN NOT
use instructions that do what I want to do.

It should not even bother an optimizer.  The optimizer takes the operations
given by the programmer, in some cases applies transformations known to 
provide the same result, and optimizes the order.  Why should an integer
and a floating point number in the same location bother it, unless that
location is a register and the (expletives deleted) hardware has different
integer and floating registers?  But even that should not befuddle the
optimizer.
> -- 
>  Paul Smee               |    JANET: Smee@uk.ac.bristol
>  Computer Centre         |   BITNET: Smee%uk.ac.bristol@ukacrl.bitnet
>  University of Bristol   | Internet: Smee%uk.ac.bristol@nsfnet-relay.ac.uk
>  (Phone: +44 272 303132) |     UUCP: ...!mcvax!ukc!gdr.bath.ac.uk!exspes


-- 
Herman Rubin, Dept. of Statistics, Purdue Univ., West Lafayette IN47907
Phone: (317)494-6054
hrubin@l.cc.purdue.edu (Internet, bitnet, UUCP)

mac@harris.cis.ksu.edu (Myron A. Calhoun) (10/12/89)

In article <1654@l.cc.purdue.edu> cik@l.cc.purdue.edu (Herman Rubin) writes:
>In article <1989Oct11.091619.18336@gdt.bath.ac.uk>, exspes@gdr.bath.ac.uk (P E Smee) writes:
>> In article <1989Oct10.185851.6490@agate.berkeley.edu> jerry@violet.berkeley.edu ( Jerry Berkman ) writes:
>< >Why not use equivalence?

 [several lines deleted]

>> Problem is, the Fortran standard *also* says that if your program tries...

 [several lines deleted]

>This is another example of those "gurus" who can not envision an intelligent
>user using the machine in an intelligent manner, and prevent that use.  I
>have deliberately used "type punning" on various machines, and I consider it
>an extremely useful tool.....

 [several lines deleted]

I agree wholeheartedly.  FORTRAN doesn't have PL/1's UNSPEC verb, yet
I have had occasion to want it.  And EQUIVALENCE provided it.
Calling a subroutine with "wrong" type parameters can also work:
   CALL NEWTYP (INTEGER,...)
       :::::
   SUBROUTINE NEWTYP (REAL,...)
--Myron
--
Myron A. Calhoun, PhD EE, W0PBV, (913) 532-6350 (work), 539-4448 (home).
INTERNET: mac@ksuvax1.cis.ksu.edu
BITNET:   mac@ksuvax1.bitnet
UUCP:  ...{rutgers, texbell}!ksuvax1!harry!mac

maine@elxsi.dfrf.nasa.gov (Richard Maine) (10/12/89)

In article <1654@l.cc.purdue.edu> cik@l.cc.purdue.edu (Herman Rubin) writes:

> ... [discussion about type punning and equivalence]

>  It should not even bother an optimizer.  The optimizer takes the operations
>  given by the programmer, in some cases applies transformations known to 
>  provide the same result, and optimizes the order.  Why should an integer
>  and a floating point number in the same location bother it, unless that
>  location is a register and the (expletives deleted) hardware has different
>  integer and floating registers?  But even that should not befuddle the
>  optimizer.

Well, you partially answered your own question.  The optimizers often
play register allocation games and this can certainly interfere with
that.  Do recall that the Fortran standard is intended to apply to
many varieties of hardware, including some that deserve the deleted
expletives.

Actually, even perfectly standard equivalences involving no type
punning can and often do mess up optimizers.  The optimizer just
"forgets" to account for the possibility of variable references
or definitions through the equivalence.  This is far from a trivial
issue.  Ok, it may not be a "good" reason, and you can bitch about
the sloppy compiler all you want (I do), but I guarantee its a real
reason.  I have seen many instances of such bugs in many compilers
(usually when helping other people debug their programs).

I try to avoid equivalence and its ilk as much as possible, both
for the usual clarity/style reasons and to lessen my exposure to
this class of compiler bugs.  Of course, "as much as possible"
doesn't mean always.  I'm guilty.  I've done it and will undoubtedly
do it again.  BUt I do regret it every time.


--

Richard Maine
maine@elxsi.dfrf.nasa.gov [130.134.1.1]

exspes@gdr.bath.ac.uk (P E Smee) (10/13/89)

In article <1654@l.cc.purdue.edu> cik@l.cc.purdue.edu (Herman Rubin) writes:
>In article <1989Oct11.091619.18336@gdt.bath.ac.uk>, exspes@gdr.bath.ac.uk (P E Smee) writes:
>> In article <1989Oct10.185851.6490@agate.berkeley.edu> jerry@violet.berkeley.edu ( Jerry Berkman ) writes:
>< >
>< >Why not use equivalence?
>< >	INTEGER I
>< >	REAL X, IX
>< >	EQUIVALENCE (X,IX)
>< >
>< >The Fortran standard specifies that a REAL and INTEGER occupy the same space.
>> Fortran equivalence was designed toallow reuse of storage on the early
>> small memory machines -- not to allow type punning.  Usually you can
>> get away with punning, but it doesn't always work and so is a bad habit.
>
>This is another example of those "gurus" who can not envision an intelligent
>user using the machine in an intelligent manner, and prevent that use.  I
>have deliberately used "type punning" on various machines, and I consider it
>an extremely useful tool.  Now, I do not mind the compiler asking me if I
>really wanted to do it, but I object to anyone telling me that I CAN NOT
>use instructions that do what I want to do.

Trust me, 'cause I don't want to get into a long discussion of FORTRAN
in a C newsgroup.  There are an incredible number of things which may
cause aliasing in FORTRAN, some of it invisible to the compiler at any
given moment due to separate compilation of modules, and so the
optimizer needs all the help it can get.  '77 FORTRAN is even more
restrictive on the user as regards possible punning and aliasing than
'66 FORTRAN was, in order primarily to permit more reliable optimization.

The need for a construct to permit type punning is clear, particularly
if you're doing 'systemmy' work.  People working on the Algol compiler
on Multics (which does even more stringent, and cross-module, type
checking) resorted to writing little PL/1 routines which simply took
whatever they were given and passed it straight back,
unchanged(bitwise) -- and declared them in the Algol code as 'foreign'
('other language module, suspend type checking') 'takes integer returns
real'.  Lies, in other words.

I tend to like things which match PL/1's 'unspec' in concept.  This
provides an explicit instruction to the compiler, and (more
importantly) a warning to future maintainers of the code, that you are
about to willfully, knowledgeably, and intentionally, cheat the data
typing and conversion rules.  Every serious language should have such a
thing.  (Unfortunately, it seems that most don't, sigh...)

-- 
 Paul Smee               |    JANET: Smee@uk.ac.bristol
 Computer Centre         |   BITNET: Smee%uk.ac.bristol@ukacrl.bitnet
 University of Bristol   | Internet: Smee%uk.ac.bristol@nsfnet-relay.ac.uk
 (Phone: +44 272 303132) |     UUCP: ...!mcvax!ukc!gdr.bath.ac.uk!exspes

pmontgom@sonia.math.ucla.edu (Peter Montgomery) (10/14/89)

In article <1989Oct13.090311.9760@gdt.bath.ac.uk> exspes@gdr.bath.ac.uk 
(P E Smee) writes:
>
>The need for a construct to permit type punning is clear, particularly
>if you're doing 'systemmy' work.  
>
>This provides an explicit instruction to the compiler, and (more
>importantly) a warning to future maintainers of the code, that you are
>about to willfully, knowledgeably, and intentionally, cheat the data
>typing and conversion rules.  Every serious language should have such a
>thing.  (Unfortunately, it seems that most don't, sigh...)
>
	If I read the June, 1989 draft F8X correctly, then the
new TRANSFER intrinsic function (p. 13-51, section 13.13.108)
will do precisely this.  The syntax is

	result = TRANSFER(SOURCE, MOLD, SIZE) .

It "returns a result with a physical representation identical to that
of SOURCE but interpreted with the type and type parameters of MOLD."
The last argument, SIZE, is optional and affects the array shape
of the result when SOURCE and MOLD have different sizes
(e.g., double precision and character).

--------
        Peter Montgomery
        pmontgom@MATH.UCLA.EDU