-
Notifications
You must be signed in to change notification settings - Fork 1k
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
Rust Roadmap: libc v1.0 release #547
Comments
Aside from the issues tagged |
I’m very opposed to making a 1.0 release just because. Upgrading from 0.1 to 0.2 was a huge pain. In Servo we had to coordinate upgrades of 52 dependencies: servo/servo#8608. Upgrading only some dependency but not others would cause build errors because they typically use some libc type (like And wasn’t just Servo. crates.io lists 1210 reverse dependencies for libc now. I think that a much better justification than just getting a nicer-looking version number should be needed to force the ecosystem to go through that again. |
It's on the official Rust Roadmap. It's very hard to argue that However, @lambda has pointed out that issue #180 needs to be resolved. If #180 were resolved, that would be a significant change, and that should warrant a big upgrade, should it not? So, one way or another, this needs to happen in 2017, and maybe we can make a significant fix to the It makes a lot of people nervous to depend on libraries that declare themselves unstable, yet |
If people feel strongly enough about the nicer-looking version number, one way that I think would be acceptable is:
@coder543 the issue you point to says “1.0-level” in the title. That’s a subjective judgment of quality, not a version number. 1.0.0 as a version number can be a signal that maintainers believe a project has this level of quality. Is this signal worth making hundreds of crates coordinate to upgrade? |
The only way I can think of that fixing #180 is a breaking change is if a crate implements the same trait separately for |
What you suggest would require breaking semver in Cargo, so I don't think that's going to happen. Would you prefer that I want Rust to have as few obstacles to being used in production as possible, and when management sees dependency on libraries that are below v1.0, that's going to be an obstacle. |
Is interfacing with the libc an essential task? I don't think so, as most of what it provides is already provided by the stdlib. Most people that depend on libc do just because it provides the |
Yes. And When a library gains in popularity, especially among other libraries that expose it in their respective public APIs, any breaking release becomes increasingly more painful. This is the "other side of the coin" of enforcing SemVer in Cargo. |
I think more important than "level of quality" is "level of stability". In a production project, I don't want to use some crate, have the project work and be deployed for a while, then suddenly need to add some new feature that depends on updating some dependent crate, and discover that due to having many recursive dependencies that were not at a stable point, having to do a whole bunch of work to clean that mess up. Essentially, the signal that 0.2.x sends me is that at some unpredictable point in the near future, I'll have to deal with the very problem you describe, of having to do a whole bunch of work to fix up a whole ecosystem of dependencies. A 1.0.0 release signals to me "we think that this is ready to support stably for a long period of time, so there won't be gratuitous ecosystem-wide semver incompatible bump in the near future". Now, is it worth actually breaking the existing ecosystem in order to help prevent this worry? I'm not sure. Simply documenting that for libc, 0.2.x is considered to be stable and supported for the long term may be sufficient, there are plenty of other widespread open source libraries that have always or for many years been under 1.0 but still considered stable. But it is worth thinking about the version number as a stability signal, rather than a quality signal. |
That's not being realistic. Breaking changes have to happen eventually or things will stagnate forever. |
Of course. “Not ever” is an exaggeration of “not unless the benefits outweighs the costs that we know (and learned the hard way) to be very high”. |
Indeed, at some point you want to commit to long-term stability, and accept the warts in the interface and work around them in backwards compatible ways. Serde in particular is the one that has bitten me the most here. But I would actually like serde to get to 1.0 so that I know when I'll stop having to be on the upgrade treadmill to keep up with the ecosystem. Right now, due to my previous experience with the API changing, I'm wary of relying on it heavily until that happens. Likewise, the 0.2 version number of libc, and previous libcpocalypse, makes me a little wary of relying on it as well. I think that while the release to bump to 1.0.0 will be painful for many of these crates, ripping off that bandaid and sending the signal that that's the last time that will happen in quite a while is the big benefit of the push to 1.0.0-level crates. There is a bit of a sense of "Rust is stable now, but the ecosystem is not" that holds people back from depending on it. |
IMHO, the Rust team should lead here, and get it to 1.0. I agree with @SimonSapin that this shouldn't be taken lightly, as it will be painful. But it should be done. |
I think the argument here is not don't do it, but don't do it unless there are meaningful breaking changes to justify it. Republishing what we have now as 1.0 just creates a ton of work to achieve a more appealing version number. The last libc breaking upgrade was a huge time sink, which we often refer to as the libc-pocalypse. I may be wrong, but I think we probably discussed calling the current version 1.0 back then for this very reason. When it does happen, I suggest not just publishing the crate and moving on. Actually do the work to get the whole ecosystem upgraded as quickly as possible; know that this is going to cause amazing grief and be prepared to help. |
It would be easier to upgrade once Cargo understands the difference between public and private dependencies, I guess – the problem last time was (AIUI) that Cargo decided to use mutually (semver-)incompatible versions of Once Cargo understands public/private dependencies, there incompatible versions of libc won't appear in one project where they're used together, so there should be no upgrade churn. Cargo issue: rust-lang/cargo#2064. |
@tbu- There will be upgrade churn even with this, given this will be a breaking bump in all projects where |
AIUI, no. People can declare their project compatible with 1.0 whenever they like, and also stay compatible with 0.2 ( |
What do you mean "stay compatible"? How? |
If a crate in your project has a public dependency on But regardless of that, if your crate exposes a |
Not if Cargo understood public dependencies. Then it would know that it can't upgrade your I link to two crates A and B, both have a public dependency on |
That doesn't work. When A updates |
Yes, it needs public dependencies first, and it needs the acknowledgement of public dependencies first. |
I'm really glad you've opened this issue. It's going to take a lot of such efforts for us to achieve the libs goals this year. FWIW, the libs team is starting to work on what it means to be 1.0 and evaluating crates with this in mind, and we'll start a public process soon to help move these crates forward (here is a very preliminary sketch of the guidelines the libs team tries to follow when evaluating apis, with a checklist at the top covering basic fit-and-finish issues). libc though is fairly special, with some unique considerations since it is entirely bindings, and may not fit into the typical crate evaluation process. Regarding the version number of this crate, I'd suggest that the notion that we are trying to get crates to 1.0, while being evocative and easy to understand, is an oversimplification. What is most important is that we get a core of critical crates up to consistent quality levels, not that they literally have a version "1.0" (e.g. some key crates are already > 1.0 but still have work to do, so they also don't fulfill the criteria of being "1.0" crates). |
I agree with this. We're not just trying to bump version numbers. But, in the process of uplifting the quality of these crates, it becomes highly logical to signal to users that they are actually and literally 1.0 levels of quality by setting the version number appropriately. Failing to do so would arguably be negligent, since it does not follow the semver guidelines, which state that 0.x.y is purely for "initial development". If a crate is at 1.0 levels of maturity, then for semver compliance alone, it should be numbered as such, since it is not in the initial development stage. I would hate for Rust crates to get into the habit of misusing the semver system out of some reluctance to release 1.0. There can always be a 2.0 or X.0 release later. 1.0 is not the end of the line. For production use, it also makes it much easier to present to coworkers and managers who are less familiar with internal Rust politics when the version numbers are appropriately set as well. The morale boost in the community from having these pervasive core crates reach v1.0 would also be tangible. There are many reasons to want to have a literal v1.0, but I don't think we should promote crates to v1.0 unless they are mature and stable in terms of both API and internal logic. Remember that "perfect is the enemy of good," so we also cannot hold the process up forever waiting on the ideal crate before releasing v1.0.
|
Yes this would help, but it wouldn’t solve the problem. When there is a conflict (crate A uses both B and C, which both have a public libc dependency) all that Cargo can do is tell you about the conflict earlier and in clearer terms than rustc would. You’ll still need to wrangle pull requests and crates.io publication in many repositories to solve the conflicts. |
@SimonSapin Perhaps the crate authors could be persuaded to support both libc versions at the same time – then the conflicts could be resolved by choosing one common version for all crates that have a public libc dependency. |
With a feature? Features are supposed to be additive. |
@nox With |
Oh. That still means coordination across all crates, and that means no improvements such as new bindings can land in libc ever, even non-breaking changes, because then the constraint would need to change to That's another problem with range constraints, they just postpone the breaking bump. |
Has anyone considered whether types in libc could benefit from as of yet unstable or unimplemented features such as untagged unions or specifying alignment? If it could, then there's no point in even trying to go to 1.0 until such features are stable. |
@dtolnay , I love the idea, even if it is "just crazy enough to work". :P But does crates.io even allow one to upload a version that is "lesser" than the most recently-published version? It would also still require the entire ecosystem to bump deps simultaneously, which might be a bit of a snarl... |
Yes, for example serde 1.0.0 was published April 20, 2017 followed by serde 0.9.16 published on April 23, 2017.
Unless I misunderstand what you mean, the whole point is to avoid the entire ecosystem having to bump deps simultaneously. Every crate that depends on libc can bump that dep independently without making their own breaking change. The approach is documented in |
You're not misunderstanding, I was just slightly mistaken in a variety of silly ways. :P Ship it! |
I don't think doing a 1.0 release just for the sake of saying this crate is 1.0 is personally worth it. However, the are a number of outstanding API-breaking issues that we might want to do at some point (finding a solution for the Right now, the |
Personally I feel it's very strange to keep oddities and hacks in the implementation and public API over doing a one time painful effort to upgrade code. No matter how painful it is. Because it's a one time thing vs getting a better API forever. I think we should aim for as many breaking changes as possible for I would feel it would be very strange to release |
The problem with platforms that make breaking API/ABI changes (BSD) #570 should in my opinion also resolved before/with 1.0 because this issue will likely cause problems in the future and is probably not fixable without breaking changes |
@snsmac we just would need to add newer target for ABI incompatible OS versions (e.g. But that's a backwards compatible change and therefore orthogonal to any libc versioning issues. We could do this today and would just need to bump the minor libc version. |
So this is my attempt at an abstracted summary of the discussion so far. First, there is a strong consensus that new
I have some opinions on these. Identifying underlying issuesWe have been able to use new Rust features in libc (e.g. Looking at some of the API-breakage issues, some of them are "this type layout changed". However, for some of them this happened because the C types are actually DSTs (e.g. using flexible-array members). So maybe using new Rust language features helps fixing these without fully breaking backwards compatibility. This leads me to the second group of issues. Platform APIs aren't timeless. Most platforms change the values of Remembering the Backwards-compatibility preserving solutionsI think there are a couple of actionable items that do not necessarily require a breaking version:
These actionable things could allow us to implement most of the "API breaking" changes that are pending without actually breaking anybody while keeping This doesn't mean that we will never do a |
As I understand it, we'd only have to do one final libcpocalypse (the second one), because with rust-lang/rfcs#1977, Cargo would understand public dependencies and thus version conflicts between two crates using different versions of libc cannot happen, because Cargo would always resolve the two crates' libc version to the same one. Is my understanding correct? |
A lot of FFI crates use libc types in their public API, so libc is a public dependency. So Cargo being aware that some (other) dependencies are private is not gonna help a lot there. However a lot of the type mismatches between libc 0.1 and 0.2 were about |
Yes, IMO this change has solved the largest headache. The point about moving the If we never release a new |
I do like the idea of having one crate for fundamental things which platforms don't have the nerve to break, and another for platform-specific things which may break at a platform's whim. If the former crate proved to be stable, small, and well-defined enough--effectively "things defined by the C standard that everything in the world relies on and it would be catastrophic for any platform to attempt to break them"--it might even be a candidate for inclusion in std someday (although I acknowledge that not everyone is on board with the idea of us standardizing even more things from the C standard, but it's hard to argue that there's any external crate that's more de-facto standardized than this crate already is). |
Hi, has there been any further discussion on this? It would be nice to have a 1.0 |
Chances are libc 0.3 will be released at some point with major backward incompatible changes, like proper usage of unions, I'm not sure whether A step towards that would be to start by removing all kernel APIs and non-stable APIs from the |
Technically the CRT on Windows is a non-stable API as it releases new major versions once in a while that can have breaking changes. |
If somebody wants to start working on this, I can mentor. A good step would be to create a new crate in this repo for a particular platform, add that as a dependency of |
* test table lookup intrinsics with negative indices * provide table lookup intrinsics only on little endian targets
2¢The libc crate is as core as any crate could possible be! 0.2.0 should have been released as 1.0.0, per your own stated policies! Hind site is of course 20/20, but its more than just cosmetic. Leaving this as is, e.g. 0.2.3921 will mean either continued risky/harmful release practices and/or fear and loathing at using new rustc features as they become available (even with the build.rs version check approach). Proposed route to a more gracefully establishing of 1.0.0, without a schism:
Please go ahead and poke holes in the above plan. I'm sure it could be improved further, but if you think it is somehow fundamentally flawed, then please propose an alternative better plan, that doesn't read "don't bother with 1.y.z", which is just a sad state, and poor resting place due to fatigue. Also: I'm not entirely insensitive to the point expressed about the platforms making Semver hard/impossible for libc. I suggest that the libc README be amended to include explanation of a "Semver best effort" release policy and how end users will be encouraged to submit PRs to backport fixes to earlier minor series, etc. The biggest distinction between this proposal and the Semver Trick previously proposed above (comment) is that this proposal doesn't risk breakage to older/infrequently published crate series that currently depend on libc (e.g. At the very least, if there is any good motivation for an 0.3 release, it really seems like it would be a waisted opportunity not to release that as 1.0.0 and get, the semver bump over with in one go. If it helps, I offer my time to make the changes/releases I propose, and writeup the rather important release notes explaining the novel approach. |
@gnzlbg Still willing to mentor this? |
libc
is the most downloaded crate of all time.Therefore, it follows logically that libc must have a v1.0 release according to the Rust roadmap.
I am opening this issue so that a plan can be formulated and then executed upon.
libc
to v1.0?1.0-breakage
, so those would need to be done, but it looks like people are holding off on doing them until closer to the currently-nebulous release date for v1.0.libc
.The text was updated successfully, but these errors were encountered: