I don't recall seeing a followup to this post. To put Michael's second suggestion into patch form, the following fixes the problem for me: --- kvm-81.orig/qemu/qemu-char.c 2008-12-14 06:16:27.000000000 -0700 +++ kvm-81/qemu/qemu-char.c 2009-02-02 14:12:20.000000000 -0700 @@ -1078,20 +1078,21 @@ if (sarg | TIOCM_DTR) *targ |= CHR_TIOCM_DTR; if (sarg | TIOCM_RTS) *targ |= CHR_TIOCM_RTS; } break; case CHR_IOCTL_SERIAL_SET_TIOCM: { int sarg = *(int *)arg; int targ = 0; + ioctl(s->fd_in, TIOCMGET, &targ); if (sarg | CHR_TIOCM_DTR) targ |= TIOCM_DTR; if (sarg | CHR_TIOCM_RTS) targ |= TIOCM_RTS; ioctl(s->fd_in, TIOCMSET, &targ); } break; default: return -ENOTSUP; } Is this approach palatable to folks? david Michael Tokarev wrote: > Michael Tokarev ?????: >> After some debugging and debugging, with a help >> Hollis Blanchard on #kvm@freenode, I discovered >> that kvm (or, rather, qemu) does not work correctly >> with serial ports, at least on linux. One problem >> report has already here, author Cc'd -- see e.g. >> http://marc.info/?l=kvm&m=122995568009533&w=2 . >> >> Here's what's going on. >> >> When opening a host's port, kvm resets the status >> lines, doing this: >> >> ioctl(13, TIOCMGET, [TIOCM_DTR|TIOCM_RTS|TIOCM_CTS|TIOCM_DSR|0x4000]) >> ioctl(13, TIOCMSET, [TIOCM_DTR|TIOCM_RTS]) >> >> which results in the following set >> >> ioctl(13, TIOCMGET, [TIOCM_DTR|TIOCM_RTS|TIOCM_CTS|TIOCM_DSR]) > > Here's the possible solution (NotAPAtch(tm)): > > In kvm-xx/qemu/qemu-char.c: > > case CHR_IOCTL_SERIAL_SET_TIOCM: > { > int sarg = *(int *)arg; > int targ = 0; <==== change this 0 to 0x4000 > if (sarg | CHR_TIOCM_DTR) > targ |= TIOCM_DTR; > if (sarg | CHR_TIOCM_RTS) > targ |= TIOCM_RTS; > ioctl(s->fd_in, TIOCMSET, &targ); > } > break; > > This is obviously a hack, esp. since this bit is not > always present even on linux (after reading 8250.c > driver). > > Real fix will be, I guess, to read the full set > first, and combine it with DTR|RTS received from > guest, something like this: > > case > { > int sarg = *(int *)arg; > int targ = 0; > ioctl(s->fd_in, TIOCMGET, &targ); > if (!(sarg | CHR_TIOCM_DTR)) > targ &= ~TIOCM_DTR; > if (!(sarg | CHR_TIOCM_RTS)) > targ ~= ~TIOCM_RTS; > ioctl(s->fd_in, TIOCMSET, &targ); > } > break; > > I.e., to always keep all the other bits, but > allow changing DTR and RTS. > > Again, I don't know how it's linux-specific, but > it seems the solution above should work on other > platforms just fine. > > /mjt -- To unsubscribe from this list: send the line "unsubscribe kvm" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html