Rust: Consider moving std::error::Error to `alloc`

Created on 8 Jul 2019  路  13Comments  路  Source: rust-lang/rust

Now that alloc is stable, this is a somewhat visible omission from no_std contexts.

In practice, it being in std means that library crates that would otherwise be no_std (+ alloc) compatible which expose some sort of error type have to either:

  1. Skip implementing std::error::Error for their error type, giving up error ergonomics for users regardless of whether or not they care about no_std
  2. Hide the implementation of std::error::Error behind a feature, which is awkward.

    • And if you already have alloc behind a feature, now you end up with separate alloc and std features (which is the option I took in one of my crates, and is mostly why I'm filing this) but is tedious, and makes your library have a larger configuration surface than feels necessary.

  3. Ignore no_std completely (what most crates do and will probably continue to do).

Bummers, all of them.

If Error is moved to alloc, while not ideal [1], it would make things easier for the relatively common case of library crates that could otherwise be no_std + alloc, but don't want to give up error handling ergonomics.


[1]: I think having Error in core makes more sense, but IIUC it can't: https://github.com/rust-lang/rust/pull/33149 (my read of this, which is probably wrong in some way, is that it's more or less because Error::downcast needs to be able to return a Box<T>)

As far as I know nothing prevents it from being in alloc (since Box is present in alloc), but I could easily be missing something important.

anyway thx for coming to my ted talk

T-libs

Most helpful comment

Hi, as a user I want to say that this would really help our projects, especially if it is adopted in serde, because it allows them to expose the same interface in std and alloc configurations

I think it (std::error not being in alloc) might also be related to problems like this: https://github.com/rust-random/rand/issues/645

All 13 comments

I think that longer term offering it in core is best, but allowing it in alloc in the meantime is a good idea.

@clarfon core doesn't have Box

@clarfon core doesn't have Box

true, but Box is only used for downcast, so that could live in alloc and the rest maybe in core? :/ not sure how to do that though.

It would require changes to how the language works, yes. But it'd be doable long term.

Hi, as a user I want to say that this would really help our projects, especially if it is adopted in serde, because it allows them to expose the same interface in std and alloc configurations

I think it (std::error not being in alloc) might also be related to problems like this: https://github.com/rust-random/rand/issues/645

Given Error::backtrace and Backtrace, it's pretty clear that doing this would need something akin to an RFC -- we need to decide how to expose Backtrace to no_std users: an opaque blob, always an empty backtrace, or something else?

Given that, closing.

@Mark-Simulacrum it was suggested in https://github.com/rust-lang/rust/pull/64017 that it can be a zero-width type, presumably with no contents

It's possible that's the right decision. I don't think it answers all the questions. I would suggest opening a PR to this repository after implementing this; if you're interested in discussing how to do so I believe internals is the right place for that.

@Mark-Simulacrum ok

I don't think I have bandwidth to do that right at this moment, but yeah i'm probably interested

If you think an RFC is the right way to go I'm also potentially interested in driving that process or participating in it, though I've never done that before

Doesn't the backtrace crate support no_std?

https://github.com/rust-lang/backtrace-rs/blob/3804dac/src/lib.rs#L67

Doesn't the backtrace crate support no_std?

I've been told

backtrace-rs could in theory be no_std and in fact std is an optional feature, although I suspect all current backends require std (maybe the goblin/addr2line backend doesn't ?)

I suspect all current backends require std (maybe the goblin/addr2line backend doesn't ?)

@shepmaster well, regardless of whether it's possible to capture a backtrace or not (that's something that can always be fixed in the future), it'd be nice to be able to use its Backtrace type in no_std + alloc environments, which would solve the aforementioned issue:

we need to decide how to expose Backtrace to no_std users: an opaque blob, always an empty backtrace, or something else?

Unfortunately I just confirmed one problem: the Backtrace type is presently gated on the std feature, ostensibly because it uses Vec. So, it seems, backtrace also needs an alloc feature as well to be able to use Vec in these environments.

That said, it seems like with a little work it should be possible to support the Backtrace type in no_std + alloc environments.

Was this page helpful?
0 / 5 - 0 ratings