Skip to content
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

Remove recursive dependency of libstd and move out functionality into separate crates #15974

Closed
mneumann opened this issue Jul 25, 2014 · 3 comments

Comments

@mneumann
Copy link
Contributor

At the moment, libstd depends for example on libnative, which itself depends on libstd. So it is not possible to compile libnative without libstd. I am not sure how rust is able to compile libstd, but I think it requires an existing libstd to compile with.

My suggestion is to factor out more parts of libstd into their own crates with non-cyclic dependencies.

  • from_str: belongs to collections, because this is where string is defined?
  • path: this can be made it's own crate libpath, if we also extract some of the common macros (see below) into their own crate.
  • os: this can be made it's own crate, if we somehow factor out io::{IoResult, IoError} from libstd.
  • libio ?

After that, for example libnative would no longer depend on libstd. I haven't looked at other libraries, but I think it's possible too to de-cycle them.

What else would need to be done?

  • deriving(Clone) right now generates code with ::std::clone::Clone while it should be ::core::clone::Clone. I think this is useful in general also for other projects that solely depend on libcore. Other derivings might have to be changed to ::core as well.
  • format_args!: same here.
  • libstd/macros.rs: fail!, assert!, assert_eq!, debug_assert!, debug_assert_eq!, unreachable!, unimplemented!, format!, try!, vec!. They shouldn't live in libstd as they might be useful in other software that depend on libcore (plus fail functionality).

If this is something we want, I can come up with some patches. Clearly more discussion is needed IMHO.

@huonw
Copy link
Member

huonw commented Jul 25, 2014

libstd only depends on libnative when building stdtest for testing, i.e. there's no recursive dependency (and it definitely doesn't depend on a version of itself). The compiler does not support circularly dependent crates at all, so it's literally impossible for them to happen. There can appear to be circular dependencies due to traits and trait objects, where some crate defines interfaces and downstream ones implement them, and are "magically" insert back to be used with the original crate.

As an example, the runtimes just implement traits from rustrt and are then manipulated via trait objects that get inserted into task-local globals. The native runtime has slightly special behaviour since it defines the start language item (see here for more info about entrypoints), and is inserted with std into every crate and so becomes the default entry point of a Rust program, but the green runtime requires manual initialisation.

from_str: belongs to collections, because this is where string is defined?

from_str takes a &str (not a String) and thus can probably be defined in libcore.

deriving(Clone) right now generates code with ::std::clone::Clone while it should be ::core::clone::Clone. I think this is useful in general also for other projects that solely depend on libcore. Other derivings might have to be changed to ::core as well.

This would require that core gets implicitly inserted along with std at the top of each crate. I'd be very interested to find a way to avoid inserting extra names into the namespace (random idea, have an attribute #[deriving_root] extern crate core; which is on std by default but can be overrided).

libstd/macros.rs: fail!, assert!, assert_eq!, debug_assert!, debug_assert_eq!, unreachable!, unimplemented!, format!, try!, vec!. They shouldn't live in libstd as they might be useful in other software that depend on libcore (plus fail functionality).

Some of them actually exist in core already.

@mneumann
Copy link
Contributor Author

Ah ok, thanks for the clarification! Makes a lot more sense now!

I wonder if these macros can be re-exported from std instead of duplication them.

I think format! can also move into core and vec! should probably be moved to collections.

@alexcrichton
Copy link
Member

Sadly we don't have a system of macro reexports now so they all have to be defined in std at the very least, and likely duplicated in core/collections.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants