]>
git.saurik.com Git - apple/xnu.git/blob - bsd/kern/tty_compat.c
2 * Copyright (c) 2000 Apple Computer, Inc. All rights reserved.
4 * @APPLE_LICENSE_HEADER_START@
6 * Copyright (c) 1999-2003 Apple Computer, Inc. All Rights Reserved.
8 * This file contains Original Code and/or Modifications of Original Code
9 * as defined in and that are subject to the Apple Public Source License
10 * Version 2.0 (the 'License'). You may not use this file except in
11 * compliance with the License. Please obtain a copy of the License at
12 * http://www.opensource.apple.com/apsl/ and read it before using this
15 * The Original Code and all software distributed under the License are
16 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
17 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
18 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
19 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
20 * Please see the License for the specific language governing rights and
21 * limitations under the License.
23 * @APPLE_LICENSE_HEADER_END@
25 /* Copyright (c) 1997 Apple Computer, Inc. All Rights Reserved */
27 * Copyright (c) 1982, 1986, 1991, 1993
28 * The Regents of the University of California. All rights reserved.
30 * Redistribution and use in source and binary forms, with or without
31 * modification, are permitted provided that the following conditions
33 * 1. Redistributions of source code must retain the above copyright
34 * notice, this list of conditions and the following disclaimer.
35 * 2. Redistributions in binary form must reproduce the above copyright
36 * notice, this list of conditions and the following disclaimer in the
37 * documentation and/or other materials provided with the distribution.
38 * 3. All advertising materials mentioning features or use of this software
39 * must display the following acknowledgement:
40 * This product includes software developed by the University of
41 * California, Berkeley and its contributors.
42 * 4. Neither the name of the University nor the names of its contributors
43 * may be used to endorse or promote products derived from this software
44 * without specific prior written permission.
46 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
47 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
48 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
49 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
50 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
51 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
52 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
53 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
54 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
55 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
58 * @(#)tty_compat.c 8.1 (Berkeley) 6/10/93
62 * mapping routines for old line discipline (yuck)
65 #include <sys/param.h>
66 #include <sys/systm.h>
67 #include <sys/ioctl.h>
70 #include <sys/termios.h>
73 #include <sys/kernel.h>
74 #include <sys/sysctl.h>
75 #include <sys/syslog.h>
77 /* NeXT Move define down here cause COMPAT_43 not valid earlier */
78 #if COMPAT_43 || defined(COMPAT_SUNOS)
80 static int ttcompatgetflags
__P((struct tty
*tp
));
81 static void ttcompatsetflags
__P((struct tty
*tp
, struct termios
*t
));
82 static void ttcompatsetlflags
__P((struct tty
*tp
, struct termios
*t
));
83 static int ttcompatspeedtab
__P((int speed
, struct speedtab
*table
));
86 static int ttydebug
= 0;
89 SYSCTL_INT(_debug
, OID_AUTO
, ttydebug
, CTLFLAG_RW
, &ttydebug
, 0, "");
92 static struct speedtab compatspeeds
[] = {
114 static int compatspcodes
[] = {
115 0, 50, 75, 110, 134, 150, 200, 300, 600, 1200,
116 1800, 2400, 4800, 9600, 19200, 38400, 57600, 115200,
120 ttcompatspeedtab(speed
, table
)
122 register struct speedtab
*table
;
125 return (0); /* hangup */
126 for ( ; table
->sp_speed
> 0; table
++)
127 if (table
->sp_speed
<= speed
) /* nearest one, rounded down */
128 return (table
->sp_code
);
129 return (1); /* 50, min and not hangup */
134 ttsetcompat(tp
, com
, data
, term
)
135 register struct tty
*tp
;
138 struct termios
*term
;
140 __private_extern__
int
141 ttsetcompat(tp
, com
, data
, term
)
142 register struct tty
*tp
;
145 struct termios
*term
;
151 register struct sgttyb
*sg
= (struct sgttyb
*)data
;
154 if ((speed
= sg
->sg_ispeed
) > MAX_SPEED
|| speed
< 0)
156 else if (speed
!= ttcompatspeedtab(tp
->t_ispeed
, compatspeeds
))
157 term
->c_ispeed
= compatspcodes
[speed
];
159 term
->c_ispeed
= tp
->t_ispeed
;
160 if ((speed
= sg
->sg_ospeed
) > MAX_SPEED
|| speed
< 0)
162 else if (speed
!= ttcompatspeedtab(tp
->t_ospeed
, compatspeeds
))
163 term
->c_ospeed
= compatspcodes
[speed
];
165 term
->c_ospeed
= tp
->t_ospeed
;
166 term
->c_cc
[VERASE
] = sg
->sg_erase
;
167 term
->c_cc
[VKILL
] = sg
->sg_kill
;
168 tp
->t_flags
= (tp
->t_flags
&0xffff0000) | (sg
->sg_flags
&0xffff);
169 ttcompatsetflags(tp
, term
);
170 *com
= (*com
== TIOCSETP
) ? TIOCSETAF
: TIOCSETA
;
174 struct tchars
*tc
= (struct tchars
*)data
;
178 cc
[VINTR
] = tc
->t_intrc
;
179 cc
[VQUIT
] = tc
->t_quitc
;
180 cc
[VSTART
] = tc
->t_startc
;
181 cc
[VSTOP
] = tc
->t_stopc
;
182 cc
[VEOF
] = tc
->t_eofc
;
183 cc
[VEOL
] = tc
->t_brkc
;
184 if (tc
->t_brkc
== -1)
185 cc
[VEOL2
] = _POSIX_VDISABLE
;
190 struct ltchars
*ltc
= (struct ltchars
*)data
;
194 cc
[VSUSP
] = ltc
->t_suspc
;
195 cc
[VDSUSP
] = ltc
->t_dsuspc
;
196 cc
[VREPRINT
] = ltc
->t_rprntc
;
197 cc
[VDISCARD
] = ltc
->t_flushc
;
198 cc
[VWERASE
] = ltc
->t_werasc
;
199 cc
[VLNEXT
] = ltc
->t_lnextc
;
206 if (*com
== TIOCLSET
)
207 tp
->t_flags
= (tp
->t_flags
&0xffff) | *(int *)data
<<16;
210 (ttcompatgetflags(tp
)&0xffff0000)|(tp
->t_flags
&0xffff);
211 if (*com
== TIOCLBIS
)
212 tp
->t_flags
|= *(int *)data
<<16;
214 tp
->t_flags
&= ~(*(int *)data
<<16);
216 ttcompatsetlflags(tp
, term
);
226 ttcompat(tp
, com
, data
, flag
)
227 register struct tty
*tp
;
232 __private_extern__
int
233 ttcompat(tp
, com
, data
, flag
, p
)
234 register struct tty
*tp
;
252 term
= tp
->t_termios
;
253 if ((error
= ttsetcompat(tp
, &com
, data
, &term
)) != 0)
256 return ttioctl(tp
, com
, (caddr_t
) &term
, flag
, p
);
258 return ttioctl(tp
, com
, &term
, flag
);
262 register struct sgttyb
*sg
= (struct sgttyb
*)data
;
263 register cc_t
*cc
= tp
->t_cc
;
265 sg
->sg_ospeed
= ttcompatspeedtab(tp
->t_ospeed
, compatspeeds
);
266 if (tp
->t_ispeed
== 0)
267 sg
->sg_ispeed
= sg
->sg_ospeed
;
269 sg
->sg_ispeed
= ttcompatspeedtab(tp
->t_ispeed
, compatspeeds
);
270 sg
->sg_erase
= cc
[VERASE
];
271 sg
->sg_kill
= cc
[VKILL
];
272 sg
->sg_flags
= tp
->t_flags
= ttcompatgetflags(tp
);
276 struct tchars
*tc
= (struct tchars
*)data
;
277 register cc_t
*cc
= tp
->t_cc
;
279 tc
->t_intrc
= cc
[VINTR
];
280 tc
->t_quitc
= cc
[VQUIT
];
281 tc
->t_startc
= cc
[VSTART
];
282 tc
->t_stopc
= cc
[VSTOP
];
283 tc
->t_eofc
= cc
[VEOF
];
284 tc
->t_brkc
= cc
[VEOL
];
288 struct ltchars
*ltc
= (struct ltchars
*)data
;
289 register cc_t
*cc
= tp
->t_cc
;
291 ltc
->t_suspc
= cc
[VSUSP
];
292 ltc
->t_dsuspc
= cc
[VDSUSP
];
293 ltc
->t_rprntc
= cc
[VREPRINT
];
294 ltc
->t_flushc
= cc
[VDISCARD
];
295 ltc
->t_werasc
= cc
[VWERASE
];
296 ltc
->t_lnextc
= cc
[VLNEXT
];
301 (ttcompatgetflags(tp
) & 0xffff0000UL
)
302 | (tp
->t_flags
& 0xffff);
303 *(int *)data
= tp
->t_flags
>>16;
306 printf("CLGET: returning %x\n", *(int *)data
);
311 *(int *)data
= tp
->t_line
? tp
->t_line
: 2;
318 return (ttioctl(tp
, TIOCSETD
,
319 *(int *)data
== 2 ? (caddr_t
)&ldisczero
: data
, flag
));
324 return (ttioctl(tp
, TIOCCONS
, data
, flag
));
329 return (ttioctl(tp
, TIOCSETD
,
330 *(int *)data
== 2 ? (caddr_t
)&ldisczero
: data
, flag
, p
));
335 return (ttioctl(tp
, TIOCCONS
, data
, flag
, p
));
338 if (tp
->t_session
== NULL
)
341 if (tp
->t_session
->s_leader
== NULL
)
344 *(int *) data
= tp
->t_session
->s_leader
->p_pid
;
356 register struct tty
*tp
;
358 register tcflag_t iflag
= tp
->t_iflag
;
359 register tcflag_t lflag
= tp
->t_lflag
;
360 register tcflag_t oflag
= tp
->t_oflag
;
361 register tcflag_t cflag
= tp
->t_cflag
;
366 if (iflag
&ICRNL
|| oflag
&ONLCR
)
368 if ((cflag
&CSIZE
) == CS8
) {
373 else if (cflag
&PARENB
) {
380 flags
|= EVENP
| ODDP
;
383 if ((lflag
&ICANON
) == 0) {
385 if (iflag
&(INPCK
|ISTRIP
|IXON
) || lflag
&(IEXTEN
|ISIG
)
386 || cflag
&(CSIZE
|PARENB
) != CS8
)
391 if (!(flags
&RAW
) && !(oflag
&OPOST
) && cflag
&(CSIZE
|PARENB
) == CS8
)
395 if ((cflag
&HUPCL
) == 0)
400 flags
|= CRTERA
|CRTBS
;
402 flags
|= CRTKIL
|CRTBS
;
407 if ((iflag
&IXANY
) == 0)
409 flags
|= lflag
&(ECHO
|TOSTOP
|FLUSHO
|PENDIN
|NOFLSH
);
412 printf("getflags: %x\n", flags
);
418 ttcompatsetflags(tp
, t
)
419 register struct tty
*tp
;
420 register struct termios
*t
;
422 register flags
= tp
->t_flags
;
423 register tcflag_t iflag
= t
->c_iflag
;
424 register tcflag_t oflag
= t
->c_oflag
;
425 register tcflag_t lflag
= t
->c_lflag
;
426 register tcflag_t cflag
= t
->c_cflag
;
430 lflag
&= ~(ECHOCTL
|ISIG
|ICANON
|IEXTEN
);
432 iflag
&= ~(PARMRK
|IGNPAR
|IGNCR
|INLCR
);
433 iflag
|= BRKINT
|IXON
|IMAXBEL
;
434 lflag
|= ISIG
|IEXTEN
|ECHOCTL
; /* XXX was echoctl on ? */
456 cflag
&= ~(CSIZE
|PARENB
);
457 if (flags
&(RAW
|LITOUT
|PASS8
)) {
459 if (!(flags
&(RAW
|PASS8
))
460 || (flags
&(RAW
|PASS8
|ANYP
)) == (PASS8
|ANYP
))
464 if (flags
&(RAW
|LITOUT
))
473 /* XXX don't set INPCK if RAW or PASS8? */
474 if ((flags
&(EVENP
|ODDP
)) == EVENP
) {
477 } else if ((flags
&(EVENP
|ODDP
)) == ODDP
) {
486 if ((flags
&DECCTQ
) == 0)
497 ttcompatsetlflags(tp
, t
)
498 register struct tty
*tp
;
499 register struct termios
*t
;
501 register flags
= tp
->t_flags
;
502 register tcflag_t iflag
= t
->c_iflag
;
503 register tcflag_t oflag
= t
->c_oflag
;
504 register tcflag_t lflag
= t
->c_lflag
;
505 register tcflag_t cflag
= t
->c_cflag
;
507 iflag
&= ~(PARMRK
|IGNPAR
|IGNCR
|INLCR
);
528 if ((flags
&DECCTQ
) == 0)
540 lflag
&= ~(TOSTOP
|FLUSHO
|PENDIN
|NOFLSH
);
541 lflag
|= flags
&(TOSTOP
|FLUSHO
|PENDIN
|NOFLSH
);
544 * The next if-else statement is copied from above so don't bother
545 * checking it separately. We could avoid fiddlling with the
546 * character size if the mode is already RAW or if neither the
547 * LITOUT bit or the PASS8 bit is being changed, but the delta of
548 * the change is not available here and skipping the RAW case would
549 * make the code different from above.
551 cflag
&= ~(CSIZE
|PARENB
);
552 if (flags
&(RAW
|LITOUT
|PASS8
)) {
554 if (!(flags
&(RAW
|PASS8
))
555 || (flags
&(RAW
|PASS8
|ANYP
)) == (PASS8
|ANYP
))
559 if (flags
&(RAW
|LITOUT
))
573 #endif /* COMPAT_43 || COMPAT_SUNOS */