C/C++ wrapper for Haskell IO monad
c++, haskell, linker, monads, static-linking
Solution
I'm going to keep this answer relatively brief because most of this is covered in the FFI documentation.
You can use the functions by calling them by name in C. The functions must be declared as `foreign export` and it parallels the `foreign import` syntax for calling functions defined in a C module in Haskell. In C, you'll need to declare the function as `extern` and give it a normal type signature.
Your `interact` function can't be declared directly because it references types that aren't defined in C. You can define and write a related function that calls `interact` in Haskell:
interact_hs :: FunPtr (CString -> CString) -> IO ()
This function would then have to use its argument (with wrapping) to call `interact`.
In C this function then appears as:
extern void interact_hs(char*(*f)(char*));
Or something like it, my function pointer syntax is rusty.
To actually call this function from C, you'll need to initialize the Haskell runtime (covered in the documentation), then call the function, at which point control of execution passes into Haskell. Once the function completes and returns, control of execution passes back into C.
Other useful resources for working with the FFI:
- GHC documentation
- Real World Haskell's chapter on the FFI
- Edward Z. Yang's blog post series on the FFI and the c2hs preprocessor
Feel free to suggest other useful links!
Problem
I want to call a Haskell function from C/C++. I have already read a few tutorials related to that topic, but IO monad calls are not covered in them. In particular, I would like to call a function that uses the `interact` function (`interact :: (String -> String) -> IO ()`). - I do not understand how to use functions in this case? - How can I declare function in C/C++ wrapper? - How control of standard input/output will be transferred between C/C++ and Haskell (in C/C++ code)?