GNU bug report logs - #33922
failing git-annex build

Previous Next

Package: guix;

Reported by: Ricardo Wurmus <rekado <at> elephly.net>

Date: Sun, 30 Dec 2018 11:54:02 UTC

Severity: normal

Done: Ricardo Wurmus <rekado <at> elephly.net>

Bug is archived. No further changes may be made.

To add a comment to this bug, you must first unarchive it, by sending
a message to control AT debbugs.gnu.org, with unarchive 33922 in the body.
You can then email your comments to 33922 AT debbugs.gnu.org in the normal way.

Toggle the display of automated, internal messages from the tracker.

View this report as an mbox folder, status mbox, maintainer mbox


Report forwarded to help-debbugs <at> gnu.org:
bug#33922; Package debbugs.gnu.org. (Sun, 30 Dec 2018 11:54:02 GMT) Full text and rfc822 format available.

Acknowledgement sent to Ricardo Wurmus <rekado <at> elephly.net>:
New bug report received and forwarded. Copy sent to help-debbugs <at> gnu.org. (Sun, 30 Dec 2018 11:54:02 GMT) Full text and rfc822 format available.

Message #5 received at submit <at> debbugs.gnu.org (full text, mbox):

From: Ricardo Wurmus <rekado <at> elephly.net>
To: Kyle Meyer <kyle <at> kyleam.com>
Cc: guix-devel <at> gnu.org
Subject: Re: failing git-annex build
Date: Sun, 30 Dec 2018 12:36:59 +0100
Hi Kyle,

> I'm seeing the failure below when trying to build git-annex.  Can anyone
> else reproduce this failure?  Any ideas how to resolve it?
>
> --8<---------------cut here---------------start------------->8---
> % git describe
> v0.16.0-400-g4f36d98f7b
>
> % ./pre-inst-env guix build -K --check git-annex
> Utility/Exception.hs:29:1: error:
>     Bad interface file: /gnu/store/qb3knv1h536sdjqc4nfkm3j1l8n7q87a-ghc-exceptions-0.10.0/lib/ghc-8.4.3/exceptions-0.10.0/Control/Monad/Catch.dyn_hi
>         Something is amiss; requested module  exceptions-0.10.0:Control.Monad.Catch differs from name found in the interface file exceptions-0.10.0:Control.Monad.Catch (if these names look the same, try again with -dppr-debug)
>    |
> 29 | import Control.Monad.Catch as X hiding (Handler)
>    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

It seems to me that this is a more general problem affecting all of our
Haskell packages.  The configure phase that you didn’t paste should show
that modules are provided by slightly different packages.

The haskell-build-system suffers from non-determinism.  It might just be
limited to the package database files that are generated by ghc-pkg
(where readdir is used and the result isn’t sorted).

I’m opening a bug report for this issue.

-- 
Ricardo





bug reassigned from package 'debbugs.gnu.org' to 'guix'. Request was from Glenn Morris <rgm <at> gnu.org> to control <at> debbugs.gnu.org. (Mon, 31 Dec 2018 21:40:02 GMT) Full text and rfc822 format available.

Information forwarded to bug-guix <at> gnu.org:
bug#33922; Package guix. (Wed, 02 Jan 2019 22:15:01 GMT) Full text and rfc822 format available.

Message #10 received at 33922 <at> debbugs.gnu.org (full text, mbox):

From: Timothy Sample <samplet <at> ngyro.com>
To: Ricardo Wurmus <rekado <at> elephly.net>
Cc: 33922 <at> debbugs.gnu.org, Kyle Meyer <kyle <at> kyleam.com>
Subject: Re: bug#33922: failing git-annex build
Date: Wed, 02 Jan 2019 17:14:38 -0500
[Message part 1 (text/plain, inline)]
Hi,

Ricardo Wurmus <rekado <at> elephly.net> writes:

> [...]
>
> It seems to me that this is a more general problem affecting all of our
> Haskell packages.  The configure phase that you didn’t paste should show
> that modules are provided by slightly different packages.
>
> The haskell-build-system suffers from non-determinism.  It might just be
> limited to the package database files that are generated by ghc-pkg
> (where readdir is used and the result isn’t sorted).

This is exactly the problem.  I’ve attached a patch that should fix
this.  Unfortunately, I kind of rediscovered this from scratch, so for
the sake of completeness, here’s all the details of what I found.

I don’t recall the exact chain of dependencies that led me from
git-annex to ghc-exceptions, but the latter is a nice and small example
of the general problem.  The ghc-exceptions package depends on ghc-stm.
Even though Hydra and Berlin built the exact same ghc-stm (save for the
“package.cache” file), the way that ghc-exceptions depends on it differs
between build servers.  Hydra uses “stm-[version]” in the ghc-exceptions
package database, and Berlin uses “stm-[version]-[hash]”.  For more
complicated packages, these differences get sufficiently jumbled up and
GHC gets grumpy because we are trying to use two “different” versions of
ghc-stm.  In this case, they both have the same name, ID, ABI, and are
even bit-for-bit identical (again, except for “package.cache”), but GHC
doesn’t care because it is worried about the different reference (with
the hash and without it).

Another concrete example is ghc-aeson.  It needs (among other things)
ghc-uuid-types and ghc-hashable.  These both need ghc-text.  Right now,
I cannot build ghc-aeson because it has conflicting requirements for
ghc-text.  It looks like I got a ghc-uuid-types substitute from Hydra
that doesn’t include the hash, and a ghc-hashable substitute from Berlin
that does.  Again, ghc-text is bit-for-bit identical between the two up
to “package.cache”.

What’s great is that both build servers are internally consistent, so
they never run into trouble.  It’s just us poor users that suffer.  :p

Obviously the “package.cache” file looks pretty guilty, but it is also
pretty inscrutable.  I pulled code out of GHC to dump a textual
representation of it, and found out that the only differences are in the
order of packages.  Everything else is the same.

I modified 'ghc-pkg' to write a sorted binary cache, and it seems to
solve all the issues mentioned above.  That is, I built ghc-text,
ghc-hashable, and ghc-uuid-types on two different computers, and got
bit-for-bit identical results for all of them.  (I also built ghc-text
on both computers without the patch, and saw the same differing
“package.cache” problem that I observed between Hydra and Berlin.)

I think this patch will solve the git-annex problem, as well improve
Haskell reproducibility.

Thoughts?


-- Tim

[0001-gnu-ghc-Sort-packages-before-writing-binary-cache.patch (text/x-patch, attachment)]

Information forwarded to bug-guix <at> gnu.org:
bug#33922; Package guix. (Sat, 05 Jan 2019 20:13:01 GMT) Full text and rfc822 format available.

Message #13 received at 33922 <at> debbugs.gnu.org (full text, mbox):

From: Kyle Meyer <kyle <at> kyleam.com>
To: Timothy Sample <samplet <at> ngyro.com>, Ricardo Wurmus <rekado <at> elephly.net>
Cc: 33922 <at> debbugs.gnu.org
Subject: Re: bug#33922: failing git-annex build
Date: Sat, 05 Jan 2019 15:12:38 -0500
Timothy Sample <samplet <at> ngyro.com> writes:

> Hi,
>
> Ricardo Wurmus <rekado <at> elephly.net> writes:
>
>> [...]
>>
>> It seems to me that this is a more general problem affecting all of our
>> Haskell packages.  The configure phase that you didn’t paste should show
>> that modules are provided by slightly different packages.
>>
>> The haskell-build-system suffers from non-determinism.  It might just be
>> limited to the package database files that are generated by ghc-pkg
>> (where readdir is used and the result isn’t sorted).
>
> This is exactly the problem.  I’ve attached a patch that should fix
> this.  Unfortunately, I kind of rediscovered this from scratch, so for
> the sake of completeness, here’s all the details of what I found.
> [...]

Interesting.  Thanks for taking the time to write up this analysis.




Information forwarded to bug-guix <at> gnu.org:
bug#33922; Package guix. (Sat, 12 Jan 2019 07:43:01 GMT) Full text and rfc822 format available.

Message #16 received at 33922 <at> debbugs.gnu.org (full text, mbox):

From: Ricardo Wurmus <rekado <at> elephly.net>
To: Timothy Sample <samplet <at> ngyro.com>
Cc: 33922 <at> debbugs.gnu.org, Kyle Meyer <kyle <at> kyleam.com>
Subject: Re: bug#33922: failing git-annex build
Date: Sat, 12 Jan 2019 08:42:20 +0100
Hi Tim,

thanks for the patch.

> From bb29ee8ccc656b86039127b31fd8b79533927053 Mon Sep 17 00:00:00 2001
> From: Timothy Sample <samplet <at> ngyro.com>
> Date: Wed, 2 Jan 2019 16:40:48 -0500
> Subject: [PATCH] gnu: ghc: Sort packages before writing binary cache.
>
> This improves the reproducibility of packages built with the Haskell
> build system.
>
> * gnu/packages/haskell.scm (ghc)[arguments]: Add a phase that patches
> 'ghc-pkg' so that it sorts packages before generating a binary cache.

Okay.

> +         ;; This phase patches the 'ghc-pkg' command so that it sorts
> +         ;; the list of packages in the binary cache it generates.
> +         (add-after 'unpack 'patch-ghc-pkg
> +           (lambda _
> +             (substitute* "utils/ghc-pkg/Main.hs"
> +               (("import Data.List")
> +                (string-append "import Data.List\n"
> +                               "import Data.Ord (comparing)"))
> +               (("pkgsCabalFormat = packages db")
> +                (string-append "pkgsCabalFormat = sortBy"
> +                               " (comparing (display . installedUnitId))"
> +                               " (packages db)")))))

This sorts the list “pkgsCabalFormat” in “updateDBCache” by the display
value of the “installedUnitId” field of each package.  According to the
documentation at [1], the UnitId type has an Ord instance, so you
probably don’t need “display”; you don’t need to sort strings but can
sort the UnitId values directly.

[1]: https://www.haskell.org/cabal/release/latest/doc/API/Cabal/Distribution-Types-UnitId.html#t:UnitId

I’m not sure about using installedUnitId here.  Is this field unique?
“sourcePackageId” is the combination of package name and version.  I
don’t understand the UnitId documentation, so I can’t say if that value
is any better.

I wonder if it would be better to sort the result of
“getDirectoryContents” instead.  As far as I understand, this is the
cause of non-determinism here.  The function “readParseDatabase” (which
contains the “getDirectoryContents” call) is used in multiple places
throughout “ghc-pkg/Main.hs”.

The most appropriate line to modify would then be this:

    confs = map (path </>) $ filter (".conf" `isSuffixOf`) fs

where “fs” is the list of FilePath values (strings).  I think you can
just do this:

    confs = map (path </>) $ filter (".conf" `isSuffixOf`) (sort fs)

because “fs” is of type [FilePath], which is [String], which is sortable
via “sort” as String has an Ord instance.

What do you think?

--
Ricardo





Information forwarded to bug-guix <at> gnu.org:
bug#33922; Package guix. (Sat, 12 Jan 2019 15:56:02 GMT) Full text and rfc822 format available.

Message #19 received at 33922 <at> debbugs.gnu.org (full text, mbox):

From: Timothy Sample <samplet <at> ngyro.com>
To: Ricardo Wurmus <rekado <at> elephly.net>
Cc: 33922 <at> debbugs.gnu.org, Kyle Meyer <kyle <at> kyleam.com>
Subject: Re: bug#33922: failing git-annex build
Date: Sat, 12 Jan 2019 10:54:55 -0500
Hi Ricardo,

Ricardo Wurmus <rekado <at> elephly.net> writes:

> Hi Tim,
>
> thanks for the patch.
>
>> From bb29ee8ccc656b86039127b31fd8b79533927053 Mon Sep 17 00:00:00 2001
>> From: Timothy Sample <samplet <at> ngyro.com>
>> Date: Wed, 2 Jan 2019 16:40:48 -0500
>> Subject: [PATCH] gnu: ghc: Sort packages before writing binary cache.
>>
>> This improves the reproducibility of packages built with the Haskell
>> build system.
>>
>> * gnu/packages/haskell.scm (ghc)[arguments]: Add a phase that patches
>> 'ghc-pkg' so that it sorts packages before generating a binary cache.
>
> Okay.
>
>> +         ;; This phase patches the 'ghc-pkg' command so that it sorts
>> +         ;; the list of packages in the binary cache it generates.
>> +         (add-after 'unpack 'patch-ghc-pkg
>> +           (lambda _
>> +             (substitute* "utils/ghc-pkg/Main.hs"
>> +               (("import Data.List")
>> +                (string-append "import Data.List\n"
>> +                               "import Data.Ord (comparing)"))
>> +               (("pkgsCabalFormat = packages db")
>> +                (string-append "pkgsCabalFormat = sortBy"
>> +                               " (comparing (display . installedUnitId))"
>> +                               " (packages db)")))))
>
> This sorts the list “pkgsCabalFormat” in “updateDBCache” by the display
> value of the “installedUnitId” field of each package.  According to the
> documentation at [1], the UnitId type has an Ord instance, so you
> probably don’t need “display”; you don’t need to sort strings but can
> sort the UnitId values directly.
>
> [1]:
> https://www.haskell.org/cabal/release/latest/doc/API/Cabal/Distribution-Types-UnitId.html#t:UnitId

Whoops!  I remember checking for an Ord instance, but I must of missed
it.  The documentation is embarrassingly clear.  :p

> I’m not sure about using installedUnitId here.  Is this field unique?
> “sourcePackageId” is the combination of package name and version.  I
> don’t understand the UnitId documentation, so I can’t say if that value
> is any better.

Based on what I see in the source code and in the cache files
themselves, this is best field.  However, I am just guessing and testing
here.  Discussion around this gets into territory I’m unfamiliar with
(I’ve never heard of a “Backpack”, for instance).

> I wonder if it would be better to sort the result of
> “getDirectoryContents” instead.  As far as I understand, this is the
> cause of non-determinism here.  The function “readParseDatabase” (which
> contains the “getDirectoryContents” call) is used in multiple places
> throughout “ghc-pkg/Main.hs”.
>
> The most appropriate line to modify would then be this:
>
>     confs = map (path </>) $ filter (".conf" `isSuffixOf`) fs
>
> where “fs” is the list of FilePath values (strings).  I think you can
> just do this:
>
>     confs = map (path </>) $ filter (".conf" `isSuffixOf`) (sort fs)
>
> because “fs” is of type [FilePath], which is [String], which is sortable
> via “sort” as String has an Ord instance.
>
> What do you think?

I thought about this approach, but I was worried it wouldn’t be so easy.
What you suggest looks pretty straight-forward though.  I will test
everything with this approach and report back.  If it works, I agree
that it is better.

Thanks for the careful review!


-- Tim




Information forwarded to bug-guix <at> gnu.org:
bug#33922; Package guix. (Tue, 15 Jan 2019 18:49:02 GMT) Full text and rfc822 format available.

Message #22 received at 33922 <at> debbugs.gnu.org (full text, mbox):

From: Timothy Sample <samplet <at> ngyro.com>
To: Ricardo Wurmus <rekado <at> elephly.net>
Cc: 33922 <at> debbugs.gnu.org, Kyle Meyer <kyle <at> kyleam.com>
Subject: Re: bug#33922: failing git-annex build
Date: Tue, 15 Jan 2019 13:48:05 -0500
Hi again,

Timothy Sample <samplet <at> ngyro.com> writes:

> Ricardo Wurmus <rekado <at> elephly.net> writes:
>>
>> [...]
>>
>> The most appropriate line to modify would then be this:
>>
>>     confs = map (path </>) $ filter (".conf" `isSuffixOf`) fs
>>
>> where “fs” is the list of FilePath values (strings).  I think you can
>> just do this:
>>
>>     confs = map (path </>) $ filter (".conf" `isSuffixOf`) (sort fs)
>>
>> because “fs” is of type [FilePath], which is [String], which is sortable
>> via “sort” as String has an Ord instance.
>>
>> What do you think?
>
> I thought about this approach, but I was worried it wouldn’t be so easy.
> What you suggest looks pretty straight-forward though.  I will test
> everything with this approach and report back.  If it works, I agree
> that it is better.

The results are in and this seems to do the trick, too.  I built GHC and
the packages I mentioned before on two different machines, and
everything came out identical.   Hence, LGTM.


-- Tim




Reply sent to Ricardo Wurmus <rekado <at> elephly.net>:
You have taken responsibility. (Thu, 17 Jan 2019 17:35:01 GMT) Full text and rfc822 format available.

Notification sent to Ricardo Wurmus <rekado <at> elephly.net>:
bug acknowledged by developer. (Thu, 17 Jan 2019 17:35:02 GMT) Full text and rfc822 format available.

Message #27 received at 33922-done <at> debbugs.gnu.org (full text, mbox):

From: Ricardo Wurmus <rekado <at> elephly.net>
To: Timothy Sample <samplet <at> ngyro.com>
Cc: 33922-done <at> debbugs.gnu.org, Kyle Meyer <kyle <at> kyleam.com>
Subject: Re: bug#33922: failing git-annex build
Date: Thu, 17 Jan 2019 18:33:55 +0100
Hi Timothy,

> The results are in and this seems to do the trick, too.  I built GHC and
> the packages I mentioned before on two different machines, and
> everything came out identical.   Hence, LGTM.

Thanks for testing!

I’ve pushed this to the master branch after waiting for ci.guix.info to
build ghc.

-- 
Ricardo





bug archived. Request was from Debbugs Internal Request <help-debbugs <at> gnu.org> to internal_control <at> debbugs.gnu.org. (Fri, 15 Feb 2019 12:24:06 GMT) Full text and rfc822 format available.

This bug report was last modified 5 years and 64 days ago.

Previous Next


GNU bug tracking system
Copyright (C) 1999 Darren O. Benham, 1997,2003 nCipher Corporation Ltd, 1994-97 Ian Jackson.