Skip to content

add Eio_unix.Sockopt for setting/getting socket options#575

Merged
talex5 merged 1 commit into
ocaml-multicore:mainfrom
avsm:sockopt
Jun 25, 2026
Merged

add Eio_unix.Sockopt for setting/getting socket options#575
talex5 merged 1 commit into
ocaml-multicore:mainfrom
avsm:sockopt

Conversation

@avsm

@avsm avsm commented Jul 7, 2023

Copy link
Copy Markdown
Contributor

There are some socket options that are Linux-specific which are quite handy to have. This adds a Eio_unix.Sockopt module which works on Eio_unix.Fd.t values.

This is a draft PR to check on the interface: the current PR replaces the need for Unix.setsockopt and has a single simple GADT for the socket options. Alternatively we could just expose the extended ones in the same style as upstream OCaml as a separate set of types, too. Opinions welcome.

Comment thread lib_eio/unix/eio_unix.mli Outdated
@patricoferris patricoferris linked an issue Jul 8, 2023 that may be closed by this pull request

@talex5 talex5 left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Seems like socket options could be useful on non-Unix systems too. We could define the type in Eio.Net as an extensible variant and put the common ones there, adding Unix specific ones in Eio_unix.Net, etc. Would have to decide what to do about unsupported options.

Comment thread lib_eio/unix/eio_unix.mli Outdated
Comment thread lib_eio/unix/eio_unix.mli Outdated
@avsm

avsm commented Jul 12, 2023

Copy link
Copy Markdown
Contributor Author

Seems like socket options could be useful on non-Unix systems too. We could define the type in Eio.Net as an extensible variant and put the common ones there, adding Unix specific ones in Eio_unix.Net, etc. Would have to decide what to do about unsupported options.

SGTM. Right now, if a given sockopt isn't defined, it becomes (-1) and a call to it raises EINVAL (similar behaviour to the OCaml Unix module).

I'll move the common definitions that work on Windows as well to Eio.Net, and then put the remaining ones in Eio_unix.

@talex5

talex5 commented Oct 2, 2024

Copy link
Copy Markdown
Collaborator

In #322, @create2000 is asking about helping to finish this. Are we happy with the current design? What needs to happen beyond rebasing it?

It looks to me like some of the options (those not specific to Unix) should move to Eio.Net (e.g. TCP_NODELAY would also make sense in a unikernel). Possibly all the options should move there; it's OK to talk about an option, even if it's not supported.

Possibly eio_unix should define e.g. type _ t += Unix_bool of Unix.socket_bool_option : bool t, so all existing OCaml options can be used.

Might need a way to pass a list of options when connecting or binding (since we do that in one step, and maybe it's too late to set some options by then?). Might want some fancy heterogeneous list to hold them, since they have various types.

@create2000 I don't know if it's a good first issue or not. It uses some fancy types and involves C code. On the other hand, it's mostly done!

@patricoferris

Copy link
Copy Markdown
Collaborator

Re:design -- my impression is that we should definitely move parts to Eio.Net that are portable, and in this instance perhaps all of the options and add the Unix version to allow for all existing OCaml options to just work. I think we will want to be able to get/set after connecting/binding anyway so this seems like a reasonable chunk of work to have in a single PR (basically what is already here, shuffled around a little)?

Perhaps a follow up PR can work to support options being set at the point of connecting/binding (as you mentioned, this seems very related to #713)?

@avsm

avsm commented Sep 27, 2025

Copy link
Copy Markdown
Contributor Author

I've pushed a rebase with all the suggestions here. There are loads of Linux and Windows specific ones to add, but I wanted to check if this is version is heading in the right direction first @talex5 @patricoferris

@avsm avsm marked this pull request as ready for review September 28, 2025 07:12

@talex5 talex5 left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

This approach looks good to me.

Comment thread lib_eio/net.ml Outdated
Comment thread lib_eio/net.mli
Comment thread lib_eio/net.mli Outdated
@avsm

avsm commented Sep 28, 2025

Copy link
Copy Markdown
Contributor Author

I've added a bunch of Linux specific calls now (skipping multicast for now, and some of the more exotic fast connect and tcp_info ones), and also dropped SO_ACCEPTCON as it's not portable to macOS with no reasonable alternative (have to do a listen and wait for an EINVAL). It can still be passed directly via the Unix passthrough, but it's not much use in Eio where you know the state of your sockets anyway.

Comment thread lib_eio_linux/eio_stubs.c Outdated
Comment thread lib_eio_linux/eio_stubs.c Outdated
@avsm

avsm commented Sep 30, 2025

Copy link
Copy Markdown
Contributor Author

Tests should be fixed now as I've pushed a fix to ignore ENOPROTOOPT errors for IP_LOCAL IP sockopts that only work on Linux >6.3

@avsm

avsm commented Sep 30, 2025

Copy link
Copy Markdown
Contributor Author

Squashed commits, should be ready for merge.

avsm added a commit to avsm/eio that referenced this pull request Sep 30, 2025

@talex5 talex5 left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

(only reviewed the mock bit so far)

Comment thread lib_eio/mock/sockopt.ml Outdated
Comment thread lib_eio/mock/sockopt.ml Outdated
Comment thread lib_eio/mock/sockopt.ml Outdated
@avsm

avsm commented Jun 13, 2026

Copy link
Copy Markdown
Contributor Author

Rebased to trunk, and some minor fixes also added while re-reviewing it.

@avsm

avsm commented Jun 13, 2026

Copy link
Copy Markdown
Contributor Author

@talex5 @patricoferris I'm happy with the low-level implementation here, but I'm not sure if the Pi integration is right. We've got a new SOCKET module type now, and I think it won't be too onerous to mock, but I'm not sure...

@avsm

avsm commented Jun 15, 2026

Copy link
Copy Markdown
Contributor Author

Need to ensure this is compatible with whatever approach we pick for #713 as well

@talex5

talex5 commented Jun 24, 2026

Copy link
Copy Markdown
Collaborator

I've merged some of this separately as #858 and #859 and rebased the remaining bit (Linux options) on them.

I then added another commit with some suggested changes:

  • Move all options to Eio.Net.Sockopt so you can try them, even if the backend might not be Linux.
  • Simplify code and tests a bit.

Comment thread lib_eio/net.mli
@talex5 talex5 force-pushed the sockopt branch 6 times, most recently from f66325d to fbd9544 Compare June 25, 2026 12:06
Comment thread lib_eio_linux/tests/network.md
Comment thread lib_eio_linux/eio_stubs.c
Comment thread lib_eio_linux/eio_stubs.c Outdated
int ret = getsockopt(Int_val(v_fd), Int_val(v_level), Int_val(v_option),
buffer, &len);
if (ret == -1) uerror("getsockopt", Nothing);
v_result = caml_alloc_initialized_string(strnlen(buffer, len), buffer);

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Nothing good comes from returning a truncated string; the caller wont be able to use it meaningully. Instead of strnlen, why not check len after the getsockopt and raise an exception if it's the same as sizeof(buffer)?

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Yes, could do. Not sure what exception to raise, though.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Invalid_argument is reasonable here. It's a rare violation that indicates something's quite wrong, and not something expected to be caught and handled.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

OK, done!

Co-authored-by: Thomas Leonard <talex5@gmail.com>
@talex5 talex5 merged commit d9558b6 into ocaml-multicore:main Jun 25, 2026
4 of 5 checks passed
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.

Support retrieving socket options

4 participants