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

Some changes to RawFdContainer #386

Merged
merged 1 commit into from
May 2, 2020
Merged

Some changes to RawFdContainer #386

merged 1 commit into from
May 2, 2020

Conversation

eduardosm
Copy link
Collaborator

@eduardosm eduardosm commented Apr 29, 2020

  • Methods are not provided at all on non-unix systems or when allow-unsafe-code is disabled. Trying to create a RawFdContainer when it is not available will cause a compile error instead of panicking at runtime.
  • drop does not panic on failure. Instead, a close method is provided that allows the caller to check for errors.
  • A try_clone method has been added. It allows to clone a RawFdContainer creating a new FD with dup.

@eduardosm eduardosm marked this pull request as draft April 29, 2020 10:37
@eduardosm
Copy link
Collaborator Author

* Methods are not provided at all on non-unix systems or when `allow-unsafe-code` is disabled.

Hmm, this is causing issues on windows + libxcb

@psychon
Copy link
Owner

psychon commented Apr 29, 2020

Basically 👍 for the PR.

Ultimately, it feels to me like that raw fd stuff is something that is not well supported by Rust. That seems like the source of some of the problems we experience.

The old code was generic enough to "support anything". No idea how to easily preserve that. Or, as Travis puts it:

error[E0277]: the trait bound `x11rb::utils::RawFdContainer: std::convert::From<std::fs::File>` is not satisfied
   --> examples/shared_memory.rs:105:10
    |
105 |     conn.shm_attach_fd(shmseg, file, false)?;
    |          ^^^^^^^^^^^^^ the trait `std::convert::From<std::fs::File>` is not implemented for `x11rb::utils::RawFdContainer`
    |
    = note: required because of the requirements on the impl of `std::convert::Into<x11rb::utils::RawFdContainer>` for `std::fs::File`

Implementing conversion for "everything" by hand cannot really work. It would only ever cover stuff that is in std and would break for any new additions to std.

Hmm, this is causing issues on windows + libxcb

That does not seem too bad and can easily be fixed with some feature checks in xcb_ffi:

rror[E0599]: no function or associated item named `into_raw_fd` found for struct `utils::raw_fd_container::RawFdContainer` in the current scope
   --> src\xcb_ffi\mod.rs:220:71
    |
220 |             let mut fds: Vec<_> = fds.into_iter().map(RawFdContainer::into_raw_fd).collect();
    |                                                                       ^^^^^^^^^^^ function or associated item not found in `utils::raw_fd_container::RawFdContainer`
    | 
   ::: src\utils.rs:182:5
    |
182 |     pub struct RawFdContainer(());
    |     ------------------------------ function or associated item `into_raw_fd` not found for this
error[E0599]: no function or associated item named `into_raw_fd` found for struct `utils::raw_fd_container::RawFdContainer` in the current scope
   --> src\xcb_ffi\mod.rs:220:71
    |
220 |             let mut fds: Vec<_> = fds.into_iter().map(RawFdContainer::into_raw_fd).collect();
    |                                                                       ^^^^^^^^^^^ function or associated item not found in `utils::raw_fd_container::RawFdContainer`
    | 
   ::: src\utils.rs:182:5
    |
182 |     pub struct RawFdContainer(());
    |     ------------------------------ function or associated item `into_raw_fd` not found for this
error: aborting due to previous error
For more information about this error, try `rustc --explain E0599`.
error: could not compile `x11rb`.

Methods are not provided at all on non-unix systems or when allow-unsafe-code is disabled. Trying to create a RawFdContainer when it is not available will cause a compile error instead of panicking at runtime.

I think originally I wanted to have the RawFdContainer type only when it would actually work, but then code in src/generated/ related to FD passing failed to compile. Having the type panic at runtime seemed like the easiest way out.

@psychon
Copy link
Owner

psychon commented May 1, 2020

Hmm, this is causing issues on windows + libxcb

You could add an explicit panic when XCBConnection receives an fd and allow-unsafe-code is disabled.

@eduardosm
Copy link
Collaborator Author

Hmm, this is causing issues on windows + libxcb

You could add an explicit panic when XCBConnection receives an fd and allow-unsafe-code is disabled.

In that case, XCBConnection would not be available at all.

I think originally I wanted to have the RawFdContainer type only when it would actually work, but then code in src/generated/ related to FD passing failed to compile. Having the type panic at runtime seemed like the easiest way out.

I was thinking adding something like a FdPassingConnection trait, that would be implemented for connections that support FD passing.

I don't have much time now, so I will continue to work on this later.

@psychon
Copy link
Owner

psychon commented May 1, 2020

I was thinking adding something like a FdPassingConnection trait, that would be implemented for connections that support FD passing.

Hm. Such a change would carry through to all of the generated code (well, at least for those extension that have FD passing stuff). And it would make the return type of x11rb::connect depend on the enabled features (which is not notice and not easily possibly).

Also, I still want to make RustConnection support FD passing, so I am not sure if it makes much sense to spend a lot of time on it.

How about using the nix crate so that nix::unixstd::close and nix::unixstd::dup are accessible without using unsafe? This is basically the route I plan for FD passing on RustConnection. However, that would still not work on Windows.

@eduardosm eduardosm force-pushed the raw-fd-container branch 3 times, most recently from 068e3d3 to a8a057b Compare May 2, 2020 17:38
@eduardosm eduardosm marked this pull request as ready for review May 2, 2020 17:49
@eduardosm eduardosm requested a review from psychon May 2, 2020 17:51
src/utils.rs Outdated
///
/// The `RawFdContainer` takes ownership of the `RawFd` and closes it on drop.
///
/// This function panics on non-unix systems.
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could you update/fix the docs? (I guess just removing the last sentence is the enough)

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done

src/utils.rs Outdated
/// with `dup`. The new `RawFdContainer` will take ownership
/// of the `dup`ed version, whereas the original `RawFdContainer`
/// will keep the ownership of is FD.
pub fn try_clone(&self) -> nix::Result<Self> {
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This makes nix appear in the public API. I think I would like to avoid that.

I would propose something like this instead:

// Nothing touched errno since sendmsg() failed
let res = res.map_err(|_| std::io::Error::last_os_error())?;

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done

src/utils.rs Outdated
/// Tries to clone the `RawFdContainer` creating a new FD
/// with `dup`. The new `RawFdContainer` will take ownership
/// of the `dup`ed version, whereas the original `RawFdContainer`
/// will keep the ownership of is FD.
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
/// will keep the ownership of is FD.
/// will keep the ownership of its FD.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed

src/utils.rs Outdated
///
/// This is similar to dropping the `RawFdContainer`, but it allows
/// the caller to handle errors.
pub fn close(self) -> nix::Result<()> {
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same as above about nix::Result appearing in the public API

src/utils.rs Outdated
/// A simple wrapper around RawFd that closes the fd on drop.
///
/// On non-unix systems, or when the `allow-unsafe-code` is disabled,
/// this type is empty and does not provide any method.
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please copy the doc from the unix version of RawFdContainer (this still talks about allow-unsafe-code)

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed

#[cfg(not(unix))]
{
// It is not possible to create a `RawFdContainer` on non-unix.
unreachable!();
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could you move the comment (or something like it) into the argument of unreachable!? (I think unreachable!("foo") should work, does it?)

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done

* Methods are not provided at all on non-unix systems or when `allow-unsafe-code` is disabled. Trying to create a `RawFdContainer` when it is not available will cause a compile error instead of panicking at runtime.
* `drop` does not panic on failure. Instead, a `close` method is provided that allows the caller to check for errors.
* A `try_clone` method has been added. It allows to clone a `RawFdContainer` creating a new FD with `dup`.
@mergify mergify bot merged commit 93ec25d into master May 2, 2020
@mergify mergify bot deleted the raw-fd-container branch May 2, 2020 19:37
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

Successfully merging this pull request may close these issues.

2 participants