}   if (ISSET(flag, O_NONBLOCK)) { if (!DEVCUA(dev) && sc->sc_cua) {  splx(s); return EBUSY; }
comopen(dev, flag, mode, p)	dev_t dev;	int flag, mode;	struct proc *p;{	int unit = DEVUNIT(dev);	struct com_softc *sc;	bus_space_tag_t iot;	bus_space_handle_t ioh;	struct tty *tp;	int s;	int error = 0; 	if (unit >= pccom_cd.cd_ndevs)		return ENXIO;	sc = pccom_cd.cd_devs[unit];	if (!sc || ISSET(sc->sc_hwflags, COM_HW_ABSENT|COM_HW_ABSENT_PENDING))		return ENXIO;	s = spltty();	if (!sc->sc_tty) {		tp = sc->sc_tty = ttymalloc();		tty_attach(tp);	} else		tp = sc->sc_tty;	splx(s);	tp->t_oproc = comstart;	tp->t_param = comparam;	tp->t_hwiflow = comhwiflow;	tp->t_dev = dev;	if (!ISSET(tp->t_state, TS_ISOPEN)) {		SET(tp->t_state, TS_WOPEN);		ttychars(tp);		tp->t_iflag = TTYDEF_IFLAG;		tp->t_oflag = TTYDEF_OFLAG;		if (ISSET(sc->sc_hwflags, COM_HW_CONSOLE))			tp->t_cflag = comconscflag;		else			tp->t_cflag = TTYDEF_CFLAG;		if (ISSET(sc->sc_swflags, COM_SW_CLOCAL))			SET(tp->t_cflag, CLOCAL);		if (ISSET(sc->sc_swflags, COM_SW_CRTSCTS))			SET(tp->t_cflag, CRTSCTS);		if (ISSET(sc->sc_swflags, COM_SW_MDMBUF))			SET(tp->t_cflag, MDMBUF);		tp->t_lflag = TTYDEF_LFLAG;		tp->t_ispeed = tp->t_ospeed = comdefaultrate;		s = spltty();		sc->sc_initialize = 1;		comparam(tp, &tp->t_termios);		ttsetwater(tp);		sc->sc_rxput = sc->sc_rxget = sc->sc_tbc = 0;		iot = sc->sc_iot;		ioh = sc->sc_ioh;		/*		 * Wake up the sleepy heads.		 */		switch (sc->sc_uarttype) {		case COM_UART_ST16650:		case COM_UART_ST16650V2:		case COM_UART_XR16850:			bus_space_write_1(iot, ioh, com_lcr, LCR_EFR);			bus_space_write_1(iot, ioh, com_efr, EFR_ECB);			bus_space_write_1(iot, ioh, com_ier, 0);			bus_space_write_1(iot, ioh, com_efr, 0);			bus_space_write_1(iot, ioh, com_lcr, 0);			break;#ifdef notyet		case COM_UART_TI16750:			bus_space_write_1(iot, ioh, com_ier, 0);			break;#endif		}#ifdef COM_HAYESP		/* Setup the ESP board */		if (ISSET(sc->sc_hwflags, COM_HW_HAYESP)) {			bus_space_handle_t hayespioh = sc->sc_hayespioh;			bus_space_write_1(iot, ioh, com_fifo,			     FIFO_DMA_MODE|FIFO_ENABLE|			     FIFO_RCV_RST|FIFO_XMT_RST|FIFO_TRIGGER_8);			/* Set 16550 compatibility mode */			bus_space_write_1(iot, hayespioh, HAYESP_CMD1, HAYESP_SETMODE);			bus_space_write_1(iot, hayespioh, HAYESP_CMD2, 			     HAYESP_MODE_FIFO|HAYESP_MODE_RTS|			     HAYESP_MODE_SCALE);			/* Set RTS/CTS flow control */			bus_space_write_1(iot, hayespioh, HAYESP_CMD1, HAYESP_SETFLOWTYPE);			bus_space_write_1(iot, hayespioh, HAYESP_CMD2, HAYESP_FLOW_RTS);			bus_space_write_1(iot, hayespioh, HAYESP_CMD2, HAYESP_FLOW_CTS);			/* Set flow control levels */			bus_space_write_1(iot, hayespioh, HAYESP_CMD1, HAYESP_SETRXFLOW);			bus_space_write_1(iot, hayespioh, HAYESP_CMD2, 			     HAYESP_HIBYTE(HAYESP_RXHIWMARK));			bus_space_write_1(iot, hayespioh, HAYESP_CMD2,			     HAYESP_LOBYTE(HAYESP_RXHIWMARK));			bus_space_write_1(iot, hayespioh, HAYESP_CMD2,			     HAYESP_HIBYTE(HAYESP_RXLOWMARK));			bus_space_write_1(iot, hayespioh, HAYESP_CMD2,			     HAYESP_LOBYTE(HAYESP_RXLOWMARK));		} else#endif		if (ISSET(sc->sc_hwflags, COM_HW_FIFO)) {			u_int8_t fifo = FIFO_ENABLE|FIFO_RCV_RST|FIFO_XMT_RST;			u_int8_t lcr;			switch (sc->sc_uarttype) {			case COM_UART_ST16650V2:				if (tp->t_ispeed <= 1200)					fifo |= FIFO_RCV_TRIGGER_8|FIFO_XMT_TRIGGER_8; /* XXX */				else					fifo |= FIFO_RCV_TRIGGER_28|FIFO_XMT_TRIGGER_30;				break;			case COM_UART_XR16850:				pccom_xr16850_fifo_init(iot, ioh);				if (tp->t_ispeed <= 1200)					fifo |= FIFO_RCV3_TRIGGER_8|FIFO_XMT3_TRIGGER_8; /* XXX */				else					fifo |= FIFO_RCV3_TRIGGER_60|FIFO_XMT3_TRIGGER_56;				break;#ifdef notyet			case COM_UART_TI16750:				fifo |= FIFO_ENABLE_64BYTE;				lcr = bus_space_read_1(iot, ioh, com_lcr);				bus_space_write_1(iot, ioh, com_lcr,				    lcr | LCR_DLAB);#endif			default:				if (tp->t_ispeed <= 1200)					fifo |= FIFO_TRIGGER_1;				else					fifo |= FIFO_TRIGGER_8;			}			/*			 * (Re)enable and drain FIFOs.			 *			 * Certain SMC chips cause problems if the FIFOs are			 * enabled while input is ready. Turn off the FIFO			 * if necessary to clear the input. Test the input			 * ready bit after enabling the FIFOs to handle races			 * between enabling and fresh input.			 *			 * Set the FIFO threshold based on the receive speed.			 */			for (;;) {			 	bus_space_write_1(iot, ioh, com_fifo, 0);				delay(100);				(void) bus_space_read_1(iot, ioh, com_data);				bus_space_write_1(iot, ioh, com_fifo, fifo |				    FIFO_RCV_RST | FIFO_XMT_RST);				delay(100);				if(!ISSET(bus_space_read_1(iot, ioh,				    com_lsr), LSR_RXRDY))				    	break;			}#ifndef notyet			if (sc->sc_uarttype == COM_UART_TI16750)				bus_space_write_1(iot, ioh, com_lcr, lcr);#endif		}		/* flush any pending I/O */		while (ISSET(bus_space_read_1(iot, ioh, com_lsr), LSR_RXRDY))			(void) bus_space_read_1(iot, ioh, com_data);		/* you turn me on, baby */		sc->sc_mcr = MCR_DTR | MCR_RTS;		if (!ISSET(sc->sc_hwflags, COM_HW_NOIEN))			SET(sc->sc_mcr, MCR_IENABLE);		bus_space_write_1(iot, ioh, com_mcr, sc->sc_mcr);		sc->sc_ier = IER_ERXRDY | IER_ERLS | IER_EMSC;		bus_space_write_1(iot, ioh, com_ier, sc->sc_ier);		sc->sc_msr = bus_space_read_1(iot, ioh, com_msr);		if (ISSET(sc->sc_swflags, COM_SW_SOFTCAR) || DEVCUA(dev) ||		    ISSET(sc->sc_msr, MSR_DCD) || ISSET(tp->t_cflag, MDMBUF))			SET(tp->t_state, TS_CARR_ON);		else			CLR(tp->t_state, TS_CARR_ON);	} else if (ISSET(tp->t_state, TS_XCLUDE) && p->p_ucred->cr_uid != 0)		return EBUSY;	else		s = spltty();	if (DEVCUA(dev)) {		if (ISSET(tp->t_state, TS_ISOPEN)) {			/* Ah, but someone already is dialed in... */			splx(s);			return EBUSY;		}		sc->sc_cua = 1;		/* We go into CUA mode */	}	/* wait for carrier if necessary */	if (ISSET(flag, O_NONBLOCK)) {		if (!DEVCUA(dev) && sc->sc_cua) {			/* Opening TTY non-blocking... but the CUA is busy */			splx(s);			return EBUSY;		}	} else {		while (sc->sc_cua ||		    (!ISSET(tp->t_cflag, CLOCAL) &&		    !ISSET(tp->t_state, TS_CARR_ON))) {			SET(tp->t_state, TS_WOPEN);			error = ttysleep(tp, &tp->t_rawq, TTIPRI | PCATCH,			    ttopen, 0);			if (!DEVCUA(dev) && sc->sc_cua && error == EINTR)				continue;			if (error) {				/* XXX should turn off chip if we're the				   only waiter */				if (DEVCUA(dev))					sc->sc_cua = 0;				CLR(tp->t_state, TS_WOPEN);				splx(s);				return error;			}			if (!DEVCUA(dev) && sc->sc_cua)				continue;		}	}	splx(s);	return (*linesw[tp->t_line].l_open)(dev, tp);}