sdl2
sdl2 copied to clipboard
Printing to stdout/stderr fails with SDL import on Windows
When importing SDL the following program will no longer print anything:
module Main
where
import qualified SDL
main :: IO ()
main = print "5"
Removing the SDL import will print as expected. My linux box's 256MB of ram is insufficient to compile the bindings so I'm assuming this issue is Windows only otherwise someone would have already noticed. I installed the bindings on Windows with these steps.
Most likely the stdout/stderr (and probably stdin) handles are getting clobbered somewhere, causing the apparent no-op? Replacing the print in the above program w/ trace similarly yields no output. Not that familiar w/ the FFI, but do the handles need to be explicitly preserved when interfacing w/ C code (e.g. SDL2)? Creating new file handles and reading/writing to them do not have any issues w/ the SDL import, fwiw
Can't reproduce:
D:\>type main.hs
module Main
where
import qualified SDL
main :: IO ()
main = print "5"
D:\>ghc main
[1 of 1] Compiling Main ( main.hs, main.o )
Linking main.exe ...
D:\>main
"5"
I used an MSYS2 package install for SDL rather than those steps, but I don't think that's relevant -- it's the same library (right down to needing that replacement SDL_platform.h
) and if anything were broken you'd be getting an error rather than nothing.
On the other hand, I'm using all 64-bit, and if you followed those instructions 100% you're using 32-bit. It's definitely plausible for there to be a bug in one but not the other. If that's not it, a broader inspection of the differences in our configurations might be helpful, though I'm honestly not sure what to look for.
Hmm I tried reinstalling sdl2 w/ 64-bit GHC + libraries w/ the instructions above but running the above program yields the same result, not printing anything. Are you using the v2.0.0 bindings @tejon?
At a quick glance, this looks a lot more like an issue with your tooling/compiler than something in sdl2. The sdl2 library doesn't execute any code at all when simply imported.
Everything I have was installed fresh yesterday, from github. Bleeding-edge current. :)
What happens if you import some other module? Try split
for one with no dependencies at all, and if that's fine maybe postgresql-simple
for something with a binary dependency that's easy to install on Windows.
@tejon changing the import to Data.List.Split
, or Linear
or Control.Lens
all builds and runs printing the output as expected, it's only the SDL
import that's no-oping. Note that I am building with ghc --make Main.hs
which should be pulling in all the dependencies automatically.
Oddly in ghci I can import SDL
and then running print does output as expected.
@polarina I checked the source and you're right I don't see any code running. This is very confusing
I have the same issue on windows 7 building with GHC 7.10.2.
The problem occurs with both 32 bit and 64 bit SDL. The files I used to build are here: https://www.sendspace.com/file/xxg33j It also includesthe SDL files I used. (http://libsdl.org/release/SDL2-devel-2.0.3-mingw.tar.gz with SDL_platform.h replaced by https://hg.libsdl.org/SDL/raw-file/e217ed463f25/include/SDL_platform.h).
The wacky_***_.bat files build/run the examples and all four of them reproduce the problem on my machine.
Thanks. I have a window machine now so may be able to work on this.
On Mon, 9 Nov 2015 11:38 pm redxaxder [email protected] wrote:
I have the same issue on windows 7 building with GHC 7.10.2.
The problem occurs with both 32 bit and 64 bit SDL. The files I used to build are here: https://www.sendspace.com/file/xxg33j It also includesthe SDL files I used. ( http://libsdl.org/release/SDL2-devel-2.0.3-mingw.tar.gz with SDL_platform.h replaced by https://hg.libsdl.org/SDL/raw-file/e217ed463f25/include/SDL_platform.h).
The wacky____*.bat files build/run the examples and all four of them reproduce the problem on my machine.
— Reply to this email directly or view it on GitHub https://github.com/haskell-game/sdl2/issues/86#issuecomment-155233674.
It seems this is an intentional SDL feature: http://sdl.beuc.net/sdl.wiki/FAQ_Console
A workaround is for windows users to recompile SDL with the right incantation.
However, the import shouldn't be triggering this behavior for sure. I'd guess there's a call to SDL_Init() hiding in the top level of the Haskell bindings.
@redxaxder just importing a package shouldn't evaluate any top-level declarations, even with unsafePerformIO
and other shenanigans. I find this issue to be strange.
Hi
Could SDL2 be redefining a symbol? (for example, SDL2 defines main)
Does the same thing happen if you use dynamic vs static linking? (the linker might prefer SDL2's function, but if you load it dynamically, it might not.)
Ivan
On 16/09/15 21:41, nxths wrote:
When importing SDL the following program will no longer print anything:
module Main where
import qualified SDL
main :: IO () main =print "5"
Removing the SDL import will print as expected. My linux box's 256MB of ram is insufficient to compile the bindings so I'm assuming this issue is Windows only otherwise someone would have already noticed. I installed the bindings on Windows with these steps https://www.reddit.com/r/haskellgamedev/comments/3kvm7z/building_and_installing_sdl2_200_sdl2image/.
Most likely the stdout/stderr (and probably stdin) handles are getting clobbered somewhere, causing the apparent no-op? Replacing the print in the above program w/ trace similarly yields no output. Not that familiar w/ the FFI, but do the handles need to be explicitly preserved when interfacing w/ C code (e.g. SDL2)? Creating new file handles and reading/writing to them do not have any issues w/ the SDL import, fwiw
— Reply to this email directly or view it on GitHub https://github.com/haskell-game/sdl2/issues/86.
I have this problem too. I'm on Windows 10 64-bit with 64-bit GHC and SDL2 2.03.
EDIT: Also when I add "sdl2" to my build-depends in cabal it stops console output as well.
I don't have this issue anymore when installing SDL2 2.0.4 w/ stack, following https://www.reddit.com/r/haskellgamedev/comments/4jpthu/windows_sdl2_is_now_almost_painless_via_stack/
Closing since this is reported fixed.
I am experiencing the same problem on windows 10, even when I installed via stack as explained in the post linked to by @nxths.
Same issue here with the latest sdl2, Windows 10 64bit.
Same issue on win7 64 bit
This issue stems from the user's system configuration of SDL2.
For my case, I installed SDL2 via msys2 (mingw64) and have the mingw64 tools in my path such that they come before Haskell Platform's mingw64 binaries.
My guess was that cabal would use pkg-config
to set up external libraries, so I found the SDL pkg-config file for mingw64: /mingw64/lib/pkgconfig/sdl2.pc
(somewhere in your msys install directory like C:\msys64\mingw64\lib\pkgconfig\sdl2.pc
).
For whatever reason, the mingw64 package is set with the option -mwindows
, which will treat the final build as a Windows application (no console opened):
Libs: -L${libdir} -lmingw32 -lSDL2main -lSDL2 -mwindows
So you can supersede this option by appending -mconsole
like so:
Libs: -L${libdir} -lmingw32 -lSDL2main -lSDL2 -mwindows -mconsole
Then in my cabal store, I deleted sdl2 to force it to reinstall with this changed configuration:
C:\Users\cro\AppData\Roaming\cabal\store\ghc-8.4.3\sdl2-2.4.1.0-669a3c6f96fa5560671e7a96610a5f0b374d164f
Rerunning the build. Note the final line is some putStrLn
from my program:
C:\Users\cro\Dropbox\Projects\distfun-hs>cabal new-run
Build profile: -w ghc-8.4.3 -O1
In order, the following will be built (use -v for more details):
- sdl2-2.4.1.0 (lib) (requires build)
- distfun-0.1.0.0 (exe:distfun) (dependency rebuilt)
Configuring sdl2-2.4.1.0 (lib)...
Building sdl2-2.4.1.0 (lib)...
ignoring (possibly broken) abi-depends field for packages
Preprocessing executable 'distfun' for distfun-0.1.0.0..
Building executable 'distfun' for distfun-0.1.0.0..
Linking C:\Users\cro\Dropbox\Projects\distfun-hs\dist-newstyle\build\x86_64-windows\ghc-8.4.3\distfun-0.1.0.0\x\distfun\build\distfun\distfun.exe ...
PROGRAM OK
I do not know how to set up my own cabal files such that dependent libraries are passed cc-options
but I figure a more flexible option would start there. Or perhaps a configuration setting in this library that passes -mconsole
on to the C compiler.
With a little extra research, I found that linking is done with ghc, so the flag can be passed with ghc-options (see https://github.com/haskell/cabal/issues/1865).
In my project's cabal file I added:
ghc-options: -optl-mconsole
Or from the command line:
cabal new-run --ghc-options="-optl-mconsole"
Of course if you did any of the above that I suggested in the previous comment, undo that and delete sdl2 from the cabal store again.
Another caveat, cabal new* seems to have some issues and this option could get stuck on. Use this to get the Windows behavior back:
cabal new-run --ghc-options="-optl-mwindows"
I'm using stack, and adding -optl-mconsole
and -optl-mwindows
to ghc-options
for the executable in the package.yaml file worked, but only after deleting the .stack-work
directory in the project's root.
My project is using sdl2-2.5.0.0
.
Thanks @cromachina!
Is there any way to make this the default behaviour for programs using this package? The behaviour is very surprising, and the plerthora of ghc/windows/utf8/crummy-cmd.exe bugs provide plenty of red herrings when trying to troubleshoot the exceptions thrown and messages not printed.
Perhaps a visible notice in the readme could help if there's no technical solution.
I'm using stack, and adding -optl-mconsole and -optl-mwindows to ghc-options for the executable in the package.yaml file
Just turn on -optl-mconsole
for the executable is OK.
Don't add -optl-mwindows
. It will cause "ERROR: stdout: commitBuffer: invalid argument (Bad file descriptor)". https://stackoverflow.com/questions/59831702/create-a-windows-executable-that-does-not-create-a-console-window
For cabal, we must delete your-project\dist-newstyle\build\x86_64-windows\ghc-xxx\your-project\x\some-executable
before build.