Re: Virtual serial port in usermode?



On 2008-01-27, Philip Pemberton <philpem@xxxxxxxxx> wrote:

Now, I've seen "softmodem" drivers for Linux that run as
daemons, process AT commands and such, and most of the ones
I've looked at use pseudo-ttys to handle the 'virtual COM
port' side of things.

Right. Just be aware that pseudo-ttys only emulate a small
subset of what a real tty does. No modem control/status
ioctls, no control over word length, parity, baud rate,
flow-control, etc.

What I haven't been able to find out is if there's a way I can
tell the OS to fire off a callback when RTS changes state (a
reset), so I can force the emulated CPU to do a full reset.

When RTS on what changes state? The only things that have an
"RTS" state are really tty devices. pty devices don't. On
real tty devices, RTS is an "output" that you set/clear. It's
not an input. Unless it's being used for flow control, the
only time RTS changes state is when you change it with an
ioctl() call.

Based on the "Linux Serial Programming HOWTO", it looks like
ioctl() calls are used to change the state of the serial
handshaking lines --

Yup, but those ioctl calls aren't implimented by the pty driver
and will just return an error condition without doing anything.
It would be very, very nice if ptys implimented those ioctl
calls and made the modem status/control bits available to the
app at the other end of the pty, but ptys don't do that.

What that means is that most any program that expects to talk
to a real tty device won't work with a pty.

is it even possible to trap these without writing a kernel
module?

I'm not 100% sure I know what you mean by "trap these", but I'm
99% sure that answer is no.

In summary, you can't do anything even close to a virtual
serial port under Linux in user-space. The pty device only
supports a fraction of the features required. So, you have to
write a serial-driver that talks to the line-discipline layer.

There are probably at least a half-dozen vendors that make
network-attached serial devices that would jump at the chance
have a workable user-space serial driver (doing network stuff
in kernel space is a PITA). But they all ended up writing
kernel modules (often coupled to user-space daemons). Using a
kernel module does get you some performance advantages over a
user-space serial driver, but it also means you get the rug
pulled out from under you about once a year when some kernel
API gets an incompatible overhaul between minor revisions of a
"stable" kernel. Unless you've got time to pay somebody to
closely follow the kernel mailing list and do continuous
testing with bleeding-edge kernels, you usually find out about
these API overhauls from customers who can no longer build the
driver.

If you can convince the linux powers-that-be to accept
additional features in the pty device, I'd be happy to help add
them. I'd _love_ to be able to a virtual serial port in
user-space (even with the reduced performance). I might even
be able to talk somebody into partially funding the effort.
But, past experiences dealing with the maintainers of Linux
kernel serial stuff haven't ever been very fruitful, and it's
probably not worth trying to maintain a "new" pty driver
outside the kernel source tree.

So, back to your problem: the easiest way to do what you want
to do is to use two real serial ports with a null-modem cable
connecting them. Even then you'll have to poll the modem
status lines, since you can't block on them. On second
thought, (IIRC) you can configure one of the ports so that when
CD drops a blocked read will be woken with an EOF. If you hook
RTS on one port to CD on the other port you then get a sort of
notification that RTS has dropped. When you close that port
and try to re-open it, the open() operation will block until CD
is active again. It's not very elegent, but it's something you
can do right now without having to do any kernel-mode
development.

Serial comm under Unix sucks. IMO, it sucks less than it does
under Windows, but it's still a nasty tricky thing to get
right.

--
Grant Edwards grante Yow! I'm ZIPPY!! Are we
at having FUN yet??
visi.com
.



Relevant Pages

  • Reference count issue with uart_close() on 2.6.16-2.6.20
    ... After that the serial port is no longer usable no matter what. ... Please find my kernel config and dmesg output below. ... # ACPI Support ... # PCI Hotplug Support ...
    (Linux-Kernel)
  • 6.0 Release kernel panic - page fault
    ... I'm experiencing kernel panics with 6.0 Release. ... port ... can't assign resources ... Additional ABI support: ...
    (freebsd-questions)
  • Random reboots on -CURRENT of 20031105
    ... Last night I cvsup-ed to -CURRENT and built world and kernel. ... pci0: <PCI bus> on pcib0 ... pci_cfgintr: 0:10 INTA BIOS irq 10 ... can't assign resources (port) ...
    (freebsd-current)
  • block driver
    ... The CF card is connected to pxa270 using VLIO interface, ... 0x87d2b810: out port ae002c a0 ... 0x87cd176c: RxInt in PIO mode.. ...
    (microsoft.public.windowsce.platbuilder)
  • Re: How to tell if a firewall alert is suspicious or not
    ... > WHY this SBCGlobal DNS server would be contacting Adobe Acrobat on port ... They have to parts, a kernel and the userland, in which programs, which are ... With Internet Protocol and TCP it is so, that any network interface in the ... To initiate a TCP connection, first the server has to "listen" on a port. ...
    (comp.security.firewalls)