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

lib/9pfs: Return ENOTSUP on ioctl requests except for FIONBIO #1098

Merged
merged 2 commits into from Oct 4, 2023

Conversation

StefanJum
Copy link
Member

Currently 9pfs returns 0 for any ioctl request (except for TIOCGWINSZ), which leads to multiple cases of files being interpreted as terminals. You can see this problem when running python scripts, since python uses ioctl calls to check if it should open up the interactive interpretor or execute a script.

Same thing could happen for other applications that rely on ioctl operations being properly executed, so the best way to go would be return EINVAL (as is used to happen before commit 28d0edf).

If the ioctl call always return EINVAL, the Ruby binary compatibility application will fail, since it tries to set O_ASYNC and breaks on error, even if it does not directly depends on that, so for now add a special case for that.

So as an overview:

  • current implementation (staging branch) -> binary compatibility python3 scripts (using glibc as the libc, since the musl case is covered by the TIOCGWINSZ special case) fails, since it thinks it runs inside a terminal.
    The same could happen for any application that expects the ioctl request to be properly handeled.
    ruby works in binary compatibility mode.
  • ioctl always returns EINVAL (as it should, since we do not handle the ioctl requests) -> python3 scripts work fine, ruby fails in binary compatibility mode, since it tries to set O_ASYNC (even if it works fine without it).
  • the implementation in this PR -> both python3 and ruby work fine, nothing else seems to currently break, even if adding the special case for FIONBIO is very hackish.

Prerequisite checklist

  • Read the contribution guidelines regarding submitting new changes to the project;
  • Tested your changes against relevant architectures and platforms;
  • Ran the checkpatch.uk on your commit series before opening this PR;
  • Updated relevant documentation.

Base target

  • Architecture(s): N/A
  • Platform(s): N/A
  • Application(s): python3 bincompat, ruby bincompat

@StefanJum StefanJum added kind/bug Something isn't working kind/quick-fix Issue is a quick fix lib/9pfs 9p client bug/runtime Bug occurs during runtime labels Sep 16, 2023
@StefanJum StefanJum requested a review from a team as a code owner September 16, 2023 11:15
@StefanJum StefanJum removed the request for review from a team September 16, 2023 11:15
@StefanJum StefanJum changed the title lib/9pfs: Return ENOTTY on ioctl tty requests lib/9pfs: Return EINVAL on ioctl requests except for FIONBIO Sep 16, 2023
Currently `9pfs` returns 0 for any `ioctl` request (except for
`TIOCGWINSZ`), which leads to multiple cases of files being interpreted
as terminals. You can see this problem when running python scripts,
since python uses `ioctl` calls to check if it should open up the
interactive interpretor or execute a script.

Same thing could happen for other applications that rely on `ioctl`
operations being properly executed, so the best way to go would be
return `ENOTSUP` (as is used to happen before commit 28d0edf).

If the `ioctl` call always return `ENOTSUP`, the Ruby binary
compatibility application will fail, since it tries to set O_ASYNC and
breaks on error, even if it does not directly depends on that, so for
now add a special case for that.

Signed-off-by: Stefan Jumarea <stefanjumarea02@gmail.com>
@StefanJum StefanJum force-pushed the StefanJum/add-ioctl-notty branch 2 times, most recently from fb43a70 to 524d0fb Compare September 20, 2023 20:40
@StefanJum
Copy link
Member Author

Updated as discussed in the application compatibility meeting @razvand @skuenzer

@StefanJum StefanJum changed the title lib/9pfs: Return EINVAL on ioctl requests except for FIONBIO lib/9pfs: Return ENOTSUP on ioctl requests except for FIONBIO Sep 20, 2023
lib/9pfs/9pfs_vnops.c Outdated Show resolved Hide resolved
@razvand
Copy link
Contributor

razvand commented Sep 27, 2023

Thanks, @StefanJum . This looks OK to me. I'm waiting for the final review, accept from @skuenzer and then I'll add my review tag.

lib/9pfs/9pfs_vnops.c Outdated Show resolved Hide resolved
lib/9pfs/9pfs_vnops.c Outdated Show resolved Hide resolved
lib/vfscore/include/vfscore/vnode.h Outdated Show resolved Hide resolved
@razvand
Copy link
Contributor

razvand commented Oct 2, 2023

@StefanJum , @mogasergiu , this looks fine with me. I'll wait for @skuenzer's confirmation that this is OK and then I'll add my reviewer tag.

Copy link
Member

@mogasergiu mogasergiu left a comment

Choose a reason for hiding this comment

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

I would also mention the fact that you introduced the new IOCTL macro's in the commit message. But other than that, LGTM! 👍

Reviewed-by: Sergiu Moga sergiu@unikraft.io

@StefanJum
Copy link
Member Author

Added the macro description in the commit message.

Some applications (e.g. python) will use `ioctl()` calls to check if an
interactive interpretor should be started or if a file should be read.

`9pfs` should respond to all terminal-related calls with an `ENOTTY`
error, so applications know that they are not running in an interactive
environment.

In order to detect the ioctl request type, add a new macro,
`IOCTL_CMD_ISTYPE(cmd, type)`, which will check the corresponding bytes
from the request number (an enhanced version of the Linux `_IOC_TYPE`).

Signed-off-by: Stefan Jumarea <stefanjumarea02@gmail.com>
#define IOCTL_CMD_ISTYPE(cmd, type) \
((cmd & (IOCTL_CMD_TYPE_MASK)) == \
(((type) << IOCTL_CMD_TYPE_SHIFT) & \
IOCTL_CMD_TYPE_MASK))
Copy link
Member

Choose a reason for hiding this comment

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

Bellísimo 💅👌

Copy link
Member

Choose a reason for hiding this comment

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

👍🏻

Copy link
Member

@skuenzer skuenzer left a comment

Choose a reason for hiding this comment

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

Thanks for your work.

Approved-by: Simon Kuenzer simon@unikraft.io

@razvand razvand merged commit 383237c into unikraft:staging Oct 4, 2023
9 checks passed
@razvand razvand deleted the StefanJum/add-ioctl-notty branch October 4, 2023 23:17
razvand pushed a commit that referenced this pull request Oct 4, 2023
Currently `9pfs` returns 0 for any `ioctl` request (except for
`TIOCGWINSZ`), which leads to multiple cases of files being interpreted
as terminals. You can see this problem when running python scripts,
since python uses `ioctl` calls to check if it should open up the
interactive interpretor or execute a script.

Same thing could happen for other applications that rely on `ioctl`
operations being properly executed, so the best way to go would be
return `ENOTSUP` (as is used to happen before commit 28d0edf).

If the `ioctl` call always return `ENOTSUP`, the Ruby binary
compatibility application will fail, since it tries to set O_ASYNC and
breaks on error, even if it does not directly depends on that, so for
now add a special case for that.

Signed-off-by: Stefan Jumarea <stefanjumarea02@gmail.com>
Reviewed-by: Sergiu Moga <sergiu@unikraft.io>
Approved-by: Simon Kuenzer <simon@unikraft.io>
GitHub-Closes: #1098
razvand pushed a commit that referenced this pull request Oct 4, 2023
Some applications (e.g. python) will use `ioctl()` calls to check if an
interactive interpretor should be started or if a file should be read.

`9pfs` should respond to all terminal-related calls with an `ENOTTY`
error, so applications know that they are not running in an interactive
environment.

In order to detect the ioctl request type, add a new macro,
`IOCTL_CMD_ISTYPE(cmd, type)`, which will check the corresponding bytes
from the request number (an enhanced version of the Linux `_IOC_TYPE`).

Signed-off-by: Stefan Jumarea <stefanjumarea02@gmail.com>
Reviewed-by: Sergiu Moga <sergiu@unikraft.io>
Approved-by: Simon Kuenzer <simon@unikraft.io>
GitHub-Closes: #1098
razvand pushed a commit that referenced this pull request Oct 20, 2023
Currently `9pfs` returns 0 for any `ioctl` request (except for
`TIOCGWINSZ`), which leads to multiple cases of files being interpreted
as terminals. You can see this problem when running python scripts,
since python uses `ioctl` calls to check if it should open up the
interactive interpretor or execute a script.

Same thing could happen for other applications that rely on `ioctl`
operations being properly executed, so the best way to go would be
return `ENOTSUP` (as is used to happen before commit 28d0edf).

If the `ioctl` call always return `ENOTSUP`, the Ruby binary
compatibility application will fail, since it tries to set O_ASYNC and
breaks on error, even if it does not directly depends on that, so for
now add a special case for that.

Signed-off-by: Stefan Jumarea <stefanjumarea02@gmail.com>
Reviewed-by: Sergiu Moga <sergiu@unikraft.io>
Approved-by: Simon Kuenzer <simon@unikraft.io>
GitHub-Closes: #1098
razvand pushed a commit that referenced this pull request Oct 20, 2023
Some applications (e.g. python) will use `ioctl()` calls to check if an
interactive interpretor should be started or if a file should be read.

`9pfs` should respond to all terminal-related calls with an `ENOTTY`
error, so applications know that they are not running in an interactive
environment.

In order to detect the ioctl request type, add a new macro,
`IOCTL_CMD_ISTYPE(cmd, type)`, which will check the corresponding bytes
from the request number (an enhanced version of the Linux `_IOC_TYPE`).

Signed-off-by: Stefan Jumarea <stefanjumarea02@gmail.com>
Reviewed-by: Sergiu Moga <sergiu@unikraft.io>
Approved-by: Simon Kuenzer <simon@unikraft.io>
GitHub-Closes: #1098
StefanJum added a commit to unikraft-upb/unikraft that referenced this pull request Dec 12, 2023
Currently ramfs returns EINVAL for any ioctl request, which leads to the
Ruby binary compatibility application to fail, since it tries to set
`O_ASYNC` and breaks on error, even if it does not directly depends on it
being set.

Add a special case to treat `O_ASYNC`, return `ENOTSUP` by default, and
return `ENOTTY` on every `ioctl()` call related to a terminal.
The implementation is similar to what we currently have in `lib/9pfs/`,
introduced by unikraft/unikraft#1098

GitHub-Fixes: unikraft#1186
Signed-off-by: Stefan Jumarea <stefanjumarea02@gmail.com>
StefanJum added a commit to unikraft-upb/unikraft that referenced this pull request Dec 12, 2023
Currently ramfs returns EINVAL for any ioctl request, which leads to the
Ruby binary compatibility application to fail, since it tries to set
`O_ASYNC` and breaks on error, even if it does not directly depends on it
being set.

Add a special case to treat `O_ASYNC`, return `ENOTSUP` by default, and
return `ENOTTY` on every `ioctl()` call related to a terminal.
The implementation is similar to what we currently have in `lib/9pfs/`,
introduced by unikraft#1098

GitHub-Fixes: unikraft#1186
Signed-off-by: Stefan Jumarea <stefanjumarea02@gmail.com>
razvand pushed a commit that referenced this pull request Dec 13, 2023
Currently ramfs returns EINVAL for any ioctl request, which leads to the
Ruby binary compatibility application to fail, since it tries to set
`O_ASYNC` and breaks on error, even if it does not directly depends on it
being set.

Add a special case to treat `O_ASYNC`, return `ENOTSUP` by default, and
return `ENOTTY` on every `ioctl()` call related to a terminal.
The implementation is similar to what we currently have in `lib/9pfs/`,
introduced by #1098

GitHub-Fixes: #1186
Signed-off-by: Stefan Jumarea <stefanjumarea02@gmail.com>
razvand pushed a commit that referenced this pull request Dec 13, 2023
Currently ramfs returns EINVAL for any ioctl request, which leads to the
Ruby binary compatibility application to fail, since it tries to set
`O_ASYNC` and breaks on error, even if it does not directly depends on it
being set.

Add a special case to treat `O_ASYNC`, return `ENOTSUP` by default, and
return `ENOTTY` on every `ioctl()` call related to a terminal.
The implementation is similar to what we currently have in `lib/9pfs/`,
introduced by #1098

Signed-off-by: Stefan Jumarea <stefanjumarea02@gmail.com>
Reviewed-by: Razvan Deaconescu <razvand@unikraft.io>
Approved-by: Razvan Deaconescu <razvand@unikraft.io>
GitHub-Fixes: #1186
GitHub-Closes: #1202
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug/runtime Bug occurs during runtime kind/bug Something isn't working kind/quick-fix Issue is a quick fix lib/9pfs 9p client
Projects
Status: Done!
Status: Done
Development

Successfully merging this pull request may close these issues.

None yet

6 participants