Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ghcid (fno-code) is twice as slow as cabal repl for my project #336

Open
jberryman opened this issue Jan 29, 2021 · 6 comments
Open

ghcid (fno-code) is twice as slow as cabal repl for my project #336

jberryman opened this issue Jan 29, 2021 · 6 comments

Comments

@jberryman
Copy link

I'm observing this with ghc 9.1 and cabal-install 3.4 and can't easily test on 8.10.2 at the moment, but the repro for 8.10.2 would look like:

  • clone https:/hasura/graphql-engine
  • cd server && ln -s cabal.project.dev-sh.local cabal.project.local
  • cabal repl (takes about 60 sec)
  • ghcid (takes something like twice that)

It looks like it's the same behavior with just cabal repl --repl-options="-fno-code"

ghcid is also slower overall after initial startup, when a file changes

Maybe this is an upstream issue, but seemed better to open it here

@ndmitchell
Copy link
Owner

When you start the project, what does it print out as the command line it uses to compile things? If you do -fno-code to cabal, are you saying its the "same behaviour" as in also slow, or also fast? If you do ghcid -c "cabal repl" does Ghcid return to the same speed or faster than Cabal repl?

@jberryman
Copy link
Author

When you start the project, what does it print out as the command line it uses to compile things?

Loading cabal repl --repl-options=-fno-code --repl-options=-fno-break-on-exception --repl-options=-fno-break-on-error --repl-options=-v1 --repl-options=-ferror-spans --repl-options=-j ...
Build profile: -w ghc-9.1.20201218 -O1
In order, the following will be built (use -v for more details):
 - graphql-engine-1.0.0 (lib) (ephemeral targets)
Preprocessing library for graphql-engine-1.0.0..
GHCi, version 9.1.20201218: https://www.haskell.org/ghc/  :? for help
[  1 of 191] Compiling Control.Arrow.Trans ( src-lib/Control/Arrow/Trans.hs, /tmp/ghc10460_0/ghc_28.o )
[  2 of 191] Compiling Control.Arrow.Extended ( src-lib/Control/Arrow/Extended.hs, /tmp/ghc10460_0/ghc_26.o )
[  3 of 191] Compiling Control.Lens.Extended ( src-lib/Control/Lens/Extended.hs, /tmp/ghc10460_0/ghc_32.o )
.... SNIP .....

If you do -fno-code to cabal, are you saying its the "same behaviour" as in also slow, or also fast?

Sorry! I mean cabal repl -fno-code is just as slow as ghcid, while just cabal repl is fast.

If you do ghcid -c "cabal repl" does Ghcid return to the same speed or faster than Cabal repl?

Yes.

In retrospect, I'm not sure why I opened this in ghcid, sorry... (I guess it seemed like the right place since it's more user-facing), but feel free to close. I'll comment here if I can open a ghc ticket with a small repro.

Is it expected that the -fno-code would show:

[  1 of 191] Compiling Control.Arrow.Trans ( src-lib/Control/Arrow/Trans.hs, /tmp/ghc10460_0/ghc_28.o )

vs, without the flag:

[  1 of 191] Compiling Control.Arrow.Trans ( src-lib/Control/Arrow/Trans.hs, interpreted )

...?

@ndmitchell
Copy link
Owner

It seems as though -fno-code on your project is causing it to compile to object files. Maybe that's something to do with template Haskell? Or just a flag out bug? Definitely one for GHC - although if it's deliberate and widespread I might change the default to not pass -fno-code.

@mpickering
Copy link

I can reproduce this but not as bad as @jberryman reports. I think it is due to how generating object files is slower than generating bytecode.

The situation is not very optimal here.

  1. TemplateHaskell is enabled in all modules so we need object files in order to run TH splices.
  2. Object files get generated and put in a temporary directory, as no specific -odir is necessarily passed. They are not reused across cabal repl calls.
  3. If you instead pass -fobject-code, initial load is slower, but reloads much faster, as object files are reused.

So I think it's a GHC bug that -fno-code can be worse than -fobject-code in some situations.

@mpickering
Copy link

Perhaps ghcide should also pass -fwrite-interface, that would make subsequent calls to ghcide potentially faster.

https://downloads.haskell.org/~ghc/latest/docs/html/users_guide/phases.html?highlight=write%20interface#ghc-flag--fwrite-interface

@ndmitchell
Copy link
Owner

One concern with -fwrite-interface is that the interface files might not go where people expect them. If ghcid has run ghci directly, they probably by default appear next to the source code. If it's via stack/cabal, the interface files might not be compatible with what stack/cabal want as they probably pass different flags. As such, anything that causes ghcid to write to disk by default seems undesirable...

But I'm not the expert here - poking ghci to get the behaviour we want is getting increasingly difficult.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants