This is a followup to my earlier question here. I've been able to get something working per Reid Barton's answer, but I notice in the core I see __pkg_ccall_GC
:
case {__pkg_ccall_GC hashabler-2.0.0 sipRound_s_x2 Word#
-> Word#
-> Word#
-> Word#
-> (# Word#, Word#, Word#, Word# #)}
ww1 ww2 ww3 (xor# ww4 b1)
Which is I think what you'd expect for a "safe" ffi call. Yet adding "unsafe" to the foreign import string is not allowed (though the error messages doesn't say why):
src/Data/Hashabler/SipHash.hs:60:1: error:
• The safe/unsafe annotation should not be used with `foreign import prim'.
• When checking declaration:
foreign import prim unsafe "static sipRound_s_x4" sipRound_s_x4#
:: Word#
-> Word# -> Word# -> Word# -> (# Word#, Word#, Word#, Word# #)
My foreign procedure is just a little but of bit-twiddling, so I don't think I want whatever the _GC
is giving me. Some relevant bits of GHC source I've looked at, FWIW and background:
compiler/prelude/ForeignCall.hs: only "Risky" omits the "_GC"
data Safety
= PlaySafe -- Might invoke Haskell GC, or do a call back, or
-- switch threads, etc. So make sure things are
-- tidy before the call. Additionally, in the threaded
-- RTS we arrange for the external call to be executed
-- by a separate OS thread, i.e., _concurrently_ to the
-- execution of other Haskell threads.
| PlayInterruptible -- Like PlaySafe, but additionally
-- the worker thread running this foreign call may
-- be unceremoniously killed, so it must be scheduled
-- on an unbound thread.
| PlayRisky -- None of the above can happen; the call will return
-- without interacting with the runtime system at all
deriving ( Eq, Show, Data )
-- Show used just for Show Lex.Token, I think
I also see some foreign import prim unsafe
and ... safe
in the GHC tree, though I suppose it's dead code. e.g. testsuite/tests/printer/Ppr046.hs
.
So my questions are:
__pkg_ccall_GC
vs a __pkg_ccall
in this case (where I'm doing foreign import prim
not ccall
)? Is it the same as described here?foreign import prim unsafe
seem to be supported?EDIT: Looking at the assembly from -ddump-asm
makes it clear nothing much is happening (shouldn't have been scared to look at the assembly), support Reid Barton's comment below:
movq %rdi,%rax
movq %r8,%rdi
xorq %r9,%rdi
movq %rsi,%rcx
movq %rax,%rsi
movq %r14,%rax
movq %rcx,%r14
movq %rbx,%rcx
movq %rax,%rbx
movq %r9,-8(%rbp)
movq %rcx,(%rbp)
addq $-16,%rbp
jmp sipRound_s_x2
The xorq
towards the top corresponds to a haskell xor
. All those movq
do seem to be a bummer though...
As Reid Barton points out the __pkg_ccall_GC
doesn't indicate anything. The code generated doesn't do the bookkeeping you would see in a safe
FFI call.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With