Skip to content

Package variants: a trivial cross-compilation solution #2476

@whitequark

Description

@whitequark

So I know there's #1536, however, that issue has too much bikeshedding for my taste. I've implemented cross-compilation for two platforms already (https://github.com/whitequark/opam-cross-windows and https://github.com/whitequark/opam-cross-android) and I think we don't need all that complexity (cross-switch dependencies etc). I have a much simpler proposal.

Let's define a notion of variant packages. A variant package differs from a regular package by a suffix in its name, e.g. re-cross:windows-x86. The suffix is available via the variable %{variant}%. This variable, as a special case, is resolved in version constraints as well as %{version}% (#1993). Since it is a constant string that can include no evaluation of its own, I don't think that presents any practical problems, and a violation of abstraction levels in opam that it entails is more a reflection of an opam's design shortcoming than any true problem.

Given a package name re-cross:VARIANT, it is resolved to an opam file as follows. If a repository has a package with the verbatim name re-cross:VARIANT, then that package's opam file is used. If not, but it has a package re-cross whose opam file includes flags: [ variant ], that package's opam file is used. Otherwise the re-cross:VARIANT package is considered nonexistent.

I'm using re-cross here since the variant mechanism is fairly generic and it may be useful for more than cross-compilation; on top of that the opam files for cross-compiled packages often differ substantially and it is not immediately obvious whether merging them with the non-cross-compiled opam file is wise. Of course, we could decide that the only use for the variant mechanism should be cross-compilation and call it something like "platform".

This is essentially the only thing that is required to support cross-compilation as a first-class citizen. Concepts like a dependency on a build component are expressed elegantly. Similarly, dependency trees are rooted in packages such as ocaml:windows-x86, which do not include flags: [ variant ]; this prevents installation of nonsensical variants.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions