Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

[Haskell-beginners] FFI and Cabal

0 views
Skip to first unread message

Jeffrey Drake

unread,
Nov 23, 2009, 2:35:15 AM11/23/09
to beginners@haskell.org Beginners Haskell

I am trying to use FFI to access some windows console functions via two simple C functions I created.

Essentially my module looks like is this:

{-# CFILES mouse.c #-}
{-# LANGUAGE ForeignFunctionInterface #-}
module Mouse where
-- import Foreign
import Foreign.C.Types


foreign import ccall unsafe "mouse.h SetupConsole" c_setupConsole :: IO CInt
foreign import ccall unsafe "mouse.h MouseEvent" c_mouseEvent :: IO CInt

setupConsole :: IO Bool
setupConsole = do c <- c_setupConsole
return $ if c == 0
then True
else False

mouseEvent :: IO (Maybe (Int, Int))
mouseEvent = do c <- c_mouseEvent
let d = toInteger c
let e = (fromInteger d)::Int

return $ if e < 0
then Nothing
else Just (e `mod` 256, e `div` 256)


It seems to compile fine. The problem comes when I need to link.
Linking dist\build\BoardGames\BoardGames.exe ...
dist\build\BoardGames\BoardGames-tmp\Mouse.o:fake:(.text+0x15): undefined reference to `SetupConsole'
dist\build\BoardGames\BoardGames-tmp\Mouse.o:fake:(.text+0x11d): undefined reference to `MouseEvent'
collect2: ld returned 1 exit status

The problem seems obvious - it isn't compiling OR linking mouse.c which is this:

#include <windows.h>

int SetupConsole()
{
HANDLE hStdin;
DWORD fdwMode, fdwSaveOldMode;
int counter=0;


hStdin = GetStdHandle(((DWORD)-10));
if (hStdin == ((HANDLE)(LONG_PTR)-1))
return -3;



if (! GetConsoleMode(hStdin, &fdwSaveOldMode) )
return -2;



fdwMode = 0x0010;
if (! SetConsoleMode(hStdin, fdwMode) )
return -1;
return 0;
}

int MouseEvent()
{
HANDLE hStdin;
INPUT_RECORD irInBuf[128];
short x, y;
unsigned i;
DWORD cNumRead;

static int ignoreNext = 0;


hStdin = GetStdHandle(((DWORD)-10));
if (hStdin == ((HANDLE)(LONG_PTR)-1))
return -2;

if (!ReadConsoleInputW(
hStdin,
irInBuf,
128,
&cNumRead) )
return -1;

for (i = 0; i < cNumRead; i++)
{
if (irInBuf[i].EventType == 0x0002 && irInBuf[i].Event.MouseEvent.dwEventFlags == 0)
{
if (ignoreNext == 1)
{
ignoreNext = 0;
return -1;
}
x = irInBuf[i].Event.MouseEvent.dwMousePosition.X;
y = irInBuf[i].Event.MouseEvent.dwMousePosition.Y;

ignoreNext = 1;

return x + (y << 8);
}
else
{
continue;
}
}
return -1;
}

So far, I have only tested this with MSVC (it works), but not with haskell platform's mingw (which includes windows.h - so I would have to wait for this...)

In my cabal file I have:
c-sources: mouse.c

So that basically sums up what I have, I just don't know how to do this. The cabal documentation says for this directive:

c-sources: filename list
A list of C source files to be compiled and linked with the Haskell files.

Which is what I expected it to do - but to no avail.

I should note that when I try to comment out with -- the c-sources line I get this:

Linking dist\build\BoardGames\BoardGames.exe ...
dist\build\BoardGames\BoardGames-tmp\Main.o:fake:(.text+0x27d): undefined reference to `__stginit_Mouse_'
dist\build\BoardGames\BoardGames-tmp\Main.o:fake:(.text+0xb4): undefined reference to `Mouse_a1_info'
dist\build\BoardGames\BoardGames-tmp\Main.o:fake:(.text+0xcc): undefined reference to `Mouse_czusetupConsole_info'
dist\build\BoardGames\BoardGames-tmp\Main.o:fake:(.text+0xf8): undefined reference to `Mouse_a1_info'
dist\build\BoardGames\BoardGames-tmp\Main.o:fake:(.text+0x17a): undefined reference to `Mouse_czusetupConsole_info'
dist\build\BoardGames\BoardGames-tmp\Main.o:fake:(.data+0x14): undefined reference to `Mouse_a1_closure'
collect2: ld returned 1 exit status


Any help that can be offered would be appreciated.

I would tell you where to find the project, but patch-tag is being unavailable for me at this time. It is the 'BoardGames' project, under iaefai.

Thank you again,
iaefai.
_______________________________________________
Beginners mailing list
Begi...@haskell.org
http://www.haskell.org/mailman/listinfo/beginners

0 new messages