adding isWHNF primop to 5.00.2 native code generator

Hi all, More mind boggling questions on prim ops :) I am happy with isWHNF that is implemented with: #define isHNFzh(r,a) r=(! closure_THUNK((StgClosure *)a)) I will re-write for the IO Monad later. I want to mimic this behaviour in the native code generator. Sigbjorn gave me this suggestion, which is based on DataToTagOp. \begin{code} primCode [res] IsHNF [arg] = let res' = amodeToStix res arg' = amodeToStix arg arg_info = StInd PtrRep arg' word_32 = StInd WordRep (StIndex PtrRep arg_info (StInt (-1))) masked_le32 = StPrim SrlOp [word_32, StInt 16] masked_be32 = StPrim AndOp [word_32, StInt 65535] #ifdef WORDS_BIGENDIAN ty_info = masked_le32 #else ty_info = masked_be32 #endif not_a_thunk = StPrim IntEqOp [ StPrim AndOp [ty_info, StInt 0x10] , StInt 0x0 ] -- ToDo: don't hardwire the value of _THUNK from InfoTables.h assign = StAssign IntRep res' not_a_thunk in returnUs (\ xs -> assign : xs) \end{code} I get different results with the version using the C macro and the native code version. In particular I get the wrong (unexpected result from the native code version). The C macro version works like this (uses these macros): #define closureFlags(c) (closure_flags[get_itbl(c)->type]) -- in ghc/includes/InfoTables.h #define closure_THUNK(c) ( closureFlags(c) & _THU) -- in ghc/includes/InfoTables.h #define get_itbl(c) (INFO_PTR_TO_STRUCT((c)->header.info)) -- in ghc/includes/ClosureMacros.h #define INFO_PTR_TO_STRUCT(info) ((StgInfoTable *)(info) - 1) -- in ghc/includes/ClosureMacros. The (-1) scares me a little bit, in INFO_PTR_TO_STRUCT. The array closure_flags[] is just a look up table, indexed by the closure type. So the key part of the code above is: get_itbl(c)->type In the native code version above, the lines below act like get_itbl(c): arg_info = StInd PtrRep arg' word_32 = StInd WordRep (StIndex PtrRep arg_info (StInt (-1))) After this I am lost. It seems to be grabbing the top or bottom 16 bits of word_32 (depending on endianness) and then ANDing those bits with 0x10 (which is the bit mask for _THU), and checking for 0. My feeling is that I should be finding out the "type" field from the closure and then switching on its value. I don't understand the native code generator well enough. I am assuming that closures are laid out the same way as via-C, in particular that there is going to be some stuff in the info table before the "type" field (this looks variable depending on how things are built). Basically I'm looking for a way to do the equivalent of "->type". Maybe there is a better way to do it. Thanks once again, and apologies if I missed something obvious. Cheers, Bernie.
participants (1)
-
Bernard James POPE