Skip to content

META: {{ stdlib("c") }} migration #2102

@h-vetinari

Description

@h-vetinari

If you got directed here by the linter...

A short overview of the situation and what to do can be found is in this announcement. For the gory details, see below...


One of the few things that conda cannot ship sanely & safely is the C standard library that is an integral part of the operating system (certainly on UNIX), and very ABI-sensitive. This is also the reason why distributions that do ship the C standard library (glibc on linux) stay on the same version for the lifetime of that distribution. Which in turn is why the glibc version is the "clock" measuring distro age in PEP600, and thus manylinux wheels (statistics).

For almost the entire duration of conda-forge's existence (AFAIU; some of this is way before my time), the underlying C standard library has not changed from:

  • glibc 2.12 from CentOS 6 (though this represents the baseline we build against; the CI image already has glibc 2.17 from CentOS 7; see here)
  • the C stdlib as of macOS 10.9 (last bump)

Given that glibc 2.12 is almost 14 years old (and CentOS 6 is EOL for over 3 years), and that macOS 10.9 is EOL since over 7 years (with Apple aggressively pushing users to upgrade), a lot of modern packages are starting to require newer, sometimes way newer glibc versions (the reason we were able to hold out so long w.r.t. OSX is that we ship our own C++ standard library, but we cannot do that for C). With the breadth of feature expansion in the C23 standard, this will also continue well into the future, as projects eventually start picking up these things.

For packages already requiring a newer C stdlib, there have been work-arounds in place for a long time:

  • - sysroot_linux-64 2.17 # [linux64]
  • - MACOSX_DEPLOYMENT_TARGET

But these are ultimately hacks, and not ready to support a wide-scale roll-out. This is what has blocked us from releasing libcxx 17.0 for example, since it requires macOS >=10.13, and would virally spread that requirement to essentially all packages that use C++ in any of their dependencies (which means +/- all of conda-forge).

The need to move to greener pastures has been clear for a long time, though the work involved is painful and it wasn't clear how to do it exactly. In any case, we've already announced that:

The latter announcement already explicitly added a caveat that we need to figure out how to do this first, because the fact that we've never really bumped the C stdlib baseline version on linux or osx, means that it's crept into lots of places as a silent assumption waiting to break. The most critical thing being correct metadata for the produced packages - in particular, if some package requires a newer C stdlib than a user has (as identified by the __glibc / __osx virtual packages; which need at least conda >=4.8), the package should not ever be installed.

After several discussions in cf/core, as well as with people from Anaconda & Prefix, we now have identified a way forward which involves a new jinja-function {{ stdlib("c") }} to match {{ compiler("c") }}. This is a welcome increase in expressivity, as indeed the version of the C standard library and compiler are very distinct things (as for other languages as well...), but with the substantial downside that no recipes are using this functionality yet. This means we have to add this function to essentially all compiled recipes, to ensure we have the mechanics in place for later bumping the minimum required version (while also allowing selective opt-ins to newer or older versions per feedstock).

The function is designed in many ways in parallel with the {{ compiler("...") }} jinja, and so the corresponding keys in conda_build_config.yaml should be unsurprising:

c_stdlib:
  - sysroot                    # [linux]
  - macosx_deployment_target   # [osx]
  - vs                         # [win]
c_stdlib_version:              # [unix]
  - 2.12                       # [linux and x86_64]
  - 2.17                       # [linux and not x86_64]
  - 10.9                       # [osx and x86_64]
  - 11.0                       # [osx and arm64]

The required functionality was merged into conda-build as of 3.28, but some bugs are still being ironed out and it'll likely not yet be fully functional until the upcoming conda-build 24.3.

This issue is intended for discussion, questions, etc. for this entire effort, beyond the specifics that will arise for glibc 2.17 resp. macos 10.13.


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