Vfile sockets
PRELIMINARY WILD HAIR IDEA THAT MAKES LITTLE SENSE
Proposal 1
In order to give our tooling the opportunity to work over serial ports as well as network ports, one idea floating around is to use vfile as a "socket adapter".
- Tools like telnet system video, gdbserver, status monitor, would be modified to use the vfile interface instead of sockets.
- Simply switching the vfile device used by the tool would switch its input/output target.
/dev/net#
A vfile driver wrapper around or replacing, to start with, the DAL E network socket interface would provide one or more /dev/net# devices, sequentially numbered, each representing one network stack instance. For most boards/users this would simply be /dev/net0.
Functions implemented on /dev/net0:
- open - Creates a socket. The file descriptor returned is the users' socket identifier.
- The "unparsed remainder" of the name can be used to specify socket type, etc. as in "/dev/net0/AF_INET/SOCK_STREAM/IPPROTO_TCP" for a TCP socket, or "/dev/net0/AF_INET/SOCK_DGRAM/IPPROTO_UDP" for a UDP socket.
- Slashes between parameters allow vfile to parse individual parameters from the "file name" using existing path-processing APIs. But it doesn't *have* to be this way.
- The "unparsed remainder" of the name can be used to specify socket type, etc. as in "/dev/net0/AF_INET/SOCK_STREAM/IPPROTO_TCP" for a TCP socket, or "/dev/net0/AF_INET/SOCK_DGRAM/IPPROTO_UDP" for a UDP socket.
- close - Destroys the socket referenced by the file descriptor.
Once a socket is opened and the user has a socket descriptor, the following additional functions are useful:
- ioctl:
- Request codes:
- IOCS_BINDING - Bind a socket to specified port.
- IOCG_BINDING - Return which port socket is currently bound to.
- IOCS_BLOCKING - Set/clear socket blocking option.
- IOCS_LISTEN - Set up listening socket (TCP).
- IOC_ACCEPT - Enter socket accepting blocking loop (TCP). On return, new socket descriptor is returned which user should then use with the vfile APIs to interact with the newly accepted client.
- IOC_CONNECT - Attempt to connect to remote peer (TCP).
- IOCS_SHUTDOWN - Gracefully close socket before closing socket descriptor.
- IOCS = I/O Control Set; IOCG = I/O Control Get
- Any request code normally passed to setsockopt - pass-thru.
- Request codes:
- read - read data from socket port.
- write - write data to socket port.
Issues/Thoughts/Concerns
What can't be handled with current vfile capabilities?
- select:
- PCR 12689 has been "on the books" for a while. epoll was implemented in the FireWire driver code directly, but could/should be made more widely available as it could be used by this driver to support select.
The above does not consider what would actually need to be done to use, for example, a UART instead of a network interface.
- Approach 1:
- Modify all UART drivers to handle ioctl request codes to make them "seem like" sockets.
- IOC_ACCEPT - wait for and return once a character is received?
- Most other socket ioctl requests can be ignored?
- IOC_ACCEPT - wait for and return once a character is received?
- Not desireable due to needing to replicate driver modifications across many drivers.
- Modify all UART drivers to handle ioctl request codes to make them "seem like" sockets.
- Approach 2:
- Allow the unparsed remainder on open of "/dev/net0" to specify a driver subordinate?
- Something like "/dev/net0/AF_INET/SOCK_STREAM/IPPROTO_TCP/uart0"
- Socket parameters processed as normal. "uart0" tells this driver to open and be a proxy between itself and /dev/uart0.
- If proxy is specified, use vfile read/write APIs. Otherwise use socket APIs?
- Something like "/dev/net0/AF_INET/SOCK_STREAM/IPPROTO_TCP/uart0"
- Allow the unparsed remainder on open of "/dev/net0" to specify a driver subordinate?
Proposal 2
Provide an adapter that permits sockets created via normal socket calls to be used via a vfile file/FILE.
Rationale:
- The protocol for constructing a socket is asymmetric and likely has socket specific semantics, e.g., bind/listen/accept vs open. Trying to hide all that under ioctl seems counter productive.
- Typical multi-server instances infrastructure typically depends on a service like inetd to hide the socket establishment part of the protocol for servers, so the primary benefit would be to provide a stdio like interface to an established stream. This model would hide much of the differences between a server servicing a socket vs interacting via a serial device.
Interesting links:
- https://deos.ddci.com/scm/Deos/products/socket/sockobj/branches/mainline/code/sockobj-session.h
- an early attempt to provide inetd vs stand-alone server abstraction for socket connections.
- https://deos.ddci.com/scm/Deos/products/status-monitor/status-monitor/branches/mainline/code/main.cpp
- An example use case. Scroll to the bottom.