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
haskell: use GHCJS to build Setup.hs for GHCJS packages #23614
Conversation
a286bd1
to
3ffd28f
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please undo the unrelated changes that introduce flatten and clarify (or remove) the added bash argument to the generic builder.
@@ -106,22 +106,22 @@ let | |||
crossCabalFlagsString = | |||
stdenv.lib.optionalString isCross (" " + stdenv.lib.concatStringsSep " " crossCabalFlags); | |||
|
|||
defaultConfigureFlags = [ | |||
defaultConfigureFlags = flatten [ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't like this change. Having a list of optional strings works just fine, IMHO, and I don't see what we gain by turning that into a list of lists that will be flattened. That feels like an unnecessary complication, and the change is certainly off-topic for this PR, which says it's about improving GHCJS support.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is a refactoring unrelated to the change, so I'm going to take it out.
Just for elaboration: The motivation (as mentioned in the PR) is that if one adds a flag to defaultConfigureFlags
that is conditional on isGhcjs
with optionalString
, a reasonable expectation, IMHO, would be that only GHCJS package derivations change and have to be rebuilt. This is not the case, since the flags are joined by concatStringsSep " "
, every empty string contributes a additional space char. Oversensitive builder scripts are a problem in general, but here it seemed especially desirable to be able to change for example the default configuration for GHCJS packages without having to rebuild the whole GHC package sets, too, for really no good reason.
Now that I think again about it, it would probably be less invasive and more robust, to use a different function than concatStringsSep
to achieve the same effect.
@@ -131,10 +131,11 @@ let | |||
"--configure-option=--host=${ghc.cross.config}" | |||
] ++ crossCabalFlags); | |||
|
|||
setupCompileFlags = [ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ditto.
@@ -1,5 +1,5 @@ | |||
{ stdenv, fetchurl, ghc, pkgconfig, glibcLocales, coreutils, gnugrep, gnused | |||
, jailbreak-cabal, hscolour, cpphs, nodePackages | |||
, jailbreak-cabal, hscolour, cpphs, bash, nodejs |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The added bash
argument here doesn't seem to be used anywhere?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Indeed, this was from a previous iteration, where I used bash in the .jsexe wrappers.
98f57ef
to
a958f37
Compare
I would like to merge this change, but there are conflicts in the generic builder. Can you please force-push a version that's rebased relative to the current |
a958f37
to
02c6859
Compare
Should be good to merge now. |
let | ||
removeLibraryHaskellDepends = pnames: depends: | ||
builtins.filter (e: !(builtins.elem (e.pname or "") pnames)) depends; | ||
addSetupDependGlobally = excludes: pset: dep: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Wouldn't it be easier to wrap the mkDerivation
function in the package set to add those dependencies? That would be one override, rather than one override per package in the whole set.
02c6859
to
b22690d
Compare
Is this better? |
Thank you very much for the effort you've put into this PR! I've merged it to |
This breaks hyperlinking Cabal, likely slows down builds (have to fire up a node instance to run Setup!), and, most seriously, breaks builds using |
As written initially the goal was to reduce the build dependencies for GHCJS packages from two compilers (GHCJS and GHC) to one (GHCJS). To me it seems odd that we would want to bring in a second independent compiler (weighing in at 1GB) for such a mundane task as compiling the Setup.hs. Setting Your PR regarding hsc2hs looks good to me. I don't know what exactly the problem is (how to use C bindings with GHCJS isn't obvious to me in the first place), but using hsc2hs from GHCJS sounds like the right default for GHCJS packages. The overhead of nodejs-run GHCJS-compiled JavaScript vs. GHC-compiled native code is a conceivable argument to bring in GHC as an optimization. I would be surprised if the difference were not dwarfed by the actual compilation done by GHCJS, after all Setup.hs typically does little more than call out to binaries, so I would probably try to benchmark it before opting against the conceptual simpler default. But if you feel strongly about it, by all means revert the change. A clean cross-compiler architecture should be able to support that. We need to distinguish between a compiler A (host -> host) used to compile the Setup.hs and a compiler B (host -> target) which is driven by the A compiled Setup.hs. We already have some logic for that in |
That makes sense, thanks. Unfortunately, the ghcjs hsc2hs uses the ghc hsc2hs under the hood, so we can't lose the dependency after all |
This is required when using ghcjs to compile Setup.hs, which we do since #23614. See comments on ghcjs/ghcjs@c35350a
/me knows nothing about ghcjs. I'll be happy with whatever solution those people come up who actually use it. |
One of the consequences of how GHCJS is compiled (first the stage1 packages, which do not include Cabal, then Cabal, and then all the stage2 packages with the previously compiled Cabal) is that the GHCJS native package-db does not include Cabal (unlike GHC). It follows that Cabal packages we want to compile with GHCJS need to depend explicitly on Cabal otherwise there will be no Cabal in the package-db to compile the Setup.hs. This wasn't a problem before since we used GHC to compile the Setup.hs which houses a Cabal in it's global package-db. I accounted for this by declaring Cabal as a Setup dependency for all sensible GHCJS packages. I guess that makes sense semantically, nonetheless I thought about different solutions, but I did not come up with something better.
With GHCJS and Cabal, executables from cabal packages are compiled to a bunch of .js files housed in folders like <exe-name>.jsexe. I provide nodejs wrappers automatically as <exe-name>, which seems to work fine. Tested with HSColour.
For testing #23611 should be applied, too, otherwise the Setup.hs compilations are of not much use and the
tasty-ant-xml
caveat mentioned there applies here as well.The
optionalString
tooptional
refactoring is done, because otherwise each conditional flag that is added triggers a rebuild of everything (even if the flag is not activated) that depends on the builder, just because a whitespace is added into the build scripts when the flags are concatenated.Motivation for this change
Currently we build the Setup.hs of cabal packages with GHC even if we use GHCJS for the actual compilation. This seems to work in general, but makes GHC as well as GHCJS a build time dependency for every cabal package compiled with GHCJS. There is also a bug in that we pass in generic-builder.nix a GHC or GHCJS package db to a command that is always GHC. GHC can not use a package-db from GHCJS, this becomes a problem if the cabal package has a dependency on a package that is also required for compiling Setup.hs, in that case the GHC native package gets shadowed.
Things done
(nix.useSandbox on NixOS,
or option
build-use-sandbox
innix.conf
on non-NixOS)
nix-shell -p nox --run "nox-review wip"
./result/bin/
)