Omer Honestly I'm out of my depth here, and so time-poor that I don't think I can realistically help much. I hope others can be more useful!
Simon | -----Original Message----- | From: Ömer Sinan Ağacan [mailto:omeraga...@gmail.com] | Sent: 10 December 2015 02:46 | To: Simon Marlow <marlo...@gmail.com>; Simon Peyton Jones | <simo...@microsoft.com>; ghc-devs <ghc-devs@haskell.org>; rwbar...@gmail.com | Subject: Re: question about coercions between primitive types in STG level | | Thanks for all the answers, | | Simon, do you remember anything about the ticket about converting between | floating point types and integers? I spend quite a bit of time in Trac | searching for this but couldn't find it. | | | Before implementing a new primop, MachOp, and code generation functions for | that I tried this: Since type signature of this new primop will be same as | float2Int# I thought maybe I should first make current implementation | working, and then I can just change the primop to coerceFloat2Int# and it | would work. | | However I'm still this same problem(illegal assembly). What I changed is I | looked at the GHC-generated, working STG code that uses float2Int#, and | tried to generate a very similar code myself. The change I had to make for | this was to use a case expression instead of let expression to bind result | of this primop. | | Here's an example. This STG is working fine: | | sat_s1Ic :: GHC.Types.Float -> | https://na01.safelinks.protection.outlook.com/?url=GHC.Types.IO&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=BnXCV6rCnP5ibif0LwHYctTd6BVA85horA1D | 1Uketrk%3d () = | \r srt:SRT:[0B :-> System.IO.print, | rUB :-> GHC.Show.$fShowInt] [ds_s1I7] | case | ds_s1I7 :: GHC.Types.Float :: Alg GHC.Types.Float | of | (wild_s1I8 :: GHC.Types.Float) | { GHC.Types.F# (f_s1I9 :: GHC.Prim.Float#) -> | case | float2Int# [(f_s1I9 :: GHC.Prim.Float#)] :: Prim | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d# | of | (sat_s1Ia :: | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d#) | { __DEFAULT -> | let { | sat_s1Ib :: | https://na01.safelinks.protection.outlook.com/?url=GHC.Types.Int&data=01%7c0 | 1%7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72 | f988bf86f141af91ab2d7cd011db47%7c1&sdata=SP%2fVPreBotFEHkZyK2Y1YSX30dEjkei6h | PARLyK11Yw%3d = | NO_CCS GHC.Types.I#! [(sat_s1Ia :: | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d#)]; | } in | System.IO.print | :: forall a_aUq. GHC.Show.Show a_aUq => a_aUq -> | https://na01.safelinks.protection.outlook.com/?url=GHC.Types.IO&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=BnXCV6rCnP5ibif0LwHYctTd6BVA85horA1D | 1Uketrk%3d () | (GHC.Show.$fShowInt :: GHC.Show.Show | https://na01.safelinks.protection.outlook.com/?url=GHC.Types.Int&data=01%7c0 | 1%7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72 | f988bf86f141af91ab2d7cd011db47%7c1&sdata=SP%2fVPreBotFEHkZyK2Y1YSX30dEjkei6h | PARLyK11Yw%3d) | (sat_s1Ib :: | https://na01.safelinks.protection.outlook.com/?url=GHC.Types.Int&data=01%7c0 | 1%7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72 | f988bf86f141af91ab2d7cd011db47%7c1&sdata=SP%2fVPreBotFEHkZyK2Y1YSX30dEjkei6h | PARLyK11Yw%3d); | }; | }; | | (Sorry for extra noisy output, I changed Outputable instances to print some | extra info) | | This code is generated by GHC for a program that uses the primop directly | and it's working. This is the code generated by my pass: | | Main.main2 :: [GHC.Types.Char] = | \u srt:SRT:[r4 :-> Main.showEither2] [] | case | case | float2Int# [1.2#] :: Prim | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d# | of | (co_g21m :: | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d#) | { __DEFAULT -> (#,#) [2## (co_g21m :: | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d#)]; | } :: UbxTup 2 | of | (sat_s21b :: (# | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d#, | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d# #)) | { (#,#) (sat_g21R :: | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d#) (sat_g21S :: | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d#) -> | Main.showEither2 | :: (# | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d#, | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d# #) -> [GHC.Types.Char] | (sat_g21R :: | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d#) (sat_g21S :: | https://na01.safelinks.protection.outlook.com/?url=GHC.Prim.Int&data=01%7c01 | %7csimonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7c72f | 988bf86f141af91ab2d7cd011db47%7c1&sdata=GMVWFJOAJ4IZj2t9WZ2hX3h7xm7U7Dbn0OfU | gjON958%3d#); | }; | | Types look correct, and I'm using a case expression to bind the result of | the primop. But generated assembly for this is still invalid! I'm wondering | if there are some invariants that I'm invalidating here, even although - | dstg-lint is passing. Does anyone know what I might be doing wrong here? | | One thing that I'm not being very careful is the information about live | variables, but I don't see how it might be related with this illegal | instruction error. | | Thanks again.. | | 2015-12-07 13:57 GMT-05:00 Simon Marlow <marlo...@gmail.com>: | > Simon's right, you need an explicit conversion, and unfortunately | > those conversions don't currently exist. You would have to add them | > to the MachOp type, and implement them in each of the native code | generators. | > | > The good news is that if you did this, we could implement cheap | > conversions between the IEEE floating point types and their | > representations as unboxed integers, which is currently done by poking | > the values to memory and then peeking them back at the desired type. | > There's a ticket for this around somewhere.... | > | > Cheers | > Simon | > | > | > On 07/12/2015 12:23, Simon Peyton Jones wrote: | >> | >> If memory serves, there are primops for converting between unboxed | >> values of different widths. | >> | >> Certainly converting between a float and a non-float will require an | >> instruction on some architectures, since they use different register | sets. | >> | >> Re (2) I have no idea. You'll need to get more information... | >> pprTrace or something. | >> | >> Simon | >> | >> | -----Original Message----- | >> | From: ghc-devs [mailto:ghc-devs-boun...@haskell.org] On Behalf Of | >> | Ömer Sinan Agacan | >> | Sent: 06 December 2015 18:25 | >> | To: ghc-devs <ghc-devs@haskell.org> | >> | Subject: question about coercions between primitive types in STG | >> | level | >> | | >> | Hi all, | >> | | >> | In my compiler pass(D1559, see ElimUbxSums.hs) I'm doing some | >> | unsafe coercions at the STG level. It works fine for lifted types, | >> | but for unlifted ones I'm having some problems. What I'm trying to | >> | do is given a number of primitive types I'm finding the one with | >> | biggest size, and then generating a constructor that takes this | >> | biggest primitive type as argument. | >> | | >> | The problem is that this is not working very well - GHC is | >> | generating illegal instructions that try to load a F32 value to a | >> | register allocated for I64, using movss instruction. | >> | | >> | CoreLint is catching this error and printing this: | >> | | >> | Cmm lint error: | >> | in basic block c1hF | >> | in assignment: | >> | _g16W::I64 = 4.5 :: W32; // CmmAssign | >> | Reg ty: I64 | >> | Rhs ty: F32 | >> | | >> | So I have two questions about this: | >> | | >> | 1. Is there a way to safely do this? What are my options here? | >> | What I'm trying | >> | to do is to use a single data constructor field for different | >> | primitive | >> | types. The field is guaranteed to be as big as necessary. | >> | | >> | 2. In the Cmm code shown above, the type annotation is showing | >> | `W32` but in the | >> | error message it says `F32`. I'm confused about this, is this | >> | error message | >> | given because the sizes don't match? (64bits vs 32bits) Why the | >> | type | >> | annotation says W32 while the value has type F32? | >> | | >> | Thanks.. | >> | _______________________________________________ | >> | ghc-devs mailing list | >> | ghc-devs@haskell.org | >> | | >> | https://na01.safelinks.protection.outlook.com/?url=http%3a%2f%2fmai | >> | l.h | >> | askell.org%2fcgi-bin%2fmailman%2flistinfo%2fghc- | >> | | >> | devs&data=01%7c01%7csimonpj%40064d.mgd.microsoft.com%7ced6a1fbfa625 | >> | 4e5 | >> | | >> | 2a7d808d2fe6a9a63%7c72f988bf86f141af91ab2d7cd011db47%7c1&sdata=7j3f | >> | Qs4 ox67SZbA4jv4uPVVdvp5X5yUUuMaqp4sh%2fpg%3d | >> _______________________________________________ | >> ghc-devs mailing list | >> ghc-devs@haskell.org | >> https://na01.safelinks.protection.outlook.com/?url=http%3a%2f%2fmail. | >> haskell.org%2fcgi-bin%2fmailman%2flistinfo%2fghc-devs&data=01%7c01%7c | >> simonpj%40064d.mgd.microsoft.com%7c900655295d074c8b867b08d3010c2165%7 | >> c72f988bf86f141af91ab2d7cd011db47%7c1&sdata=DYbGX1f9UBqSTEN9qDWBiqM9H | >> ucMEitgBCnh4ZZjneg%3d | >> | > _______________________________________________ ghc-devs mailing list ghc-devs@haskell.org http://mail.haskell.org/cgi-bin/mailman/listinfo/ghc-devs