TermPrimSetPty.c 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785
  1. /*
  2. * CDE - Common Desktop Environment
  3. *
  4. * Copyright (c) 1993-2012, The Open Group. All rights reserved.
  5. *
  6. * These libraries and programs are free software; you can
  7. * redistribute them and/or modify them under the terms of the GNU
  8. * Lesser General Public License as published by the Free Software
  9. * Foundation; either version 2 of the License, or (at your option)
  10. * any later version.
  11. *
  12. * These libraries and programs are distributed in the hope that
  13. * they will be useful, but WITHOUT ANY WARRANTY; without even the
  14. * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
  15. * PURPOSE. See the GNU Lesser General Public License for more
  16. * details.
  17. *
  18. * You should have received a copy of the GNU Lesser General Public
  19. * License along with these libraries and programs; if not, write
  20. * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
  21. * Floor, Boston, MA 02110-1301 USA
  22. */
  23. /* *
  24. * (c) Copyright 1993, 1994, 1996 Hewlett-Packard Company *
  25. * (c) Copyright 1993, 1994, 1996 International Business Machines Corp. *
  26. * (c) Copyright 1993, 1994, 1996 Sun Microsystems, Inc. *
  27. * (c) Copyright 1993, 1994, 1996 Novell, Inc. *
  28. * (c) Copyright 1996 Digital Equipment Corporation. *
  29. * (c) Copyright 1996 FUJITSU LIMITED. *
  30. * (c) Copyright 1996 Hitachi. *
  31. */
  32. #include "TermHeader.h"
  33. #include "TermPrimOSDepI.h"
  34. #include "TermPrimDebug.h"
  35. #include <fcntl.h>
  36. #ifdef ALPHA_ARCHITECTURE
  37. #include <sys/ioctl.h>
  38. #include <sys/ttydev.h>
  39. #endif /* ALPHA_ARCHITECTURE */
  40. #include <termios.h>
  41. #ifdef USE_PTYS
  42. #ifdef HP_ARCHITECTURE
  43. #include <sys/ptyio.h>
  44. #endif /* HP_ARCHITECTURE */
  45. #endif /* USE_PTYS */
  46. #if defined(HP_ARCHITECTURE) && !(OSMAJORVERSION > 9)
  47. #include <bsdtty.h>
  48. #endif /* defined(HP_ARCHITECTURE) && !(OSMAJORVERSION > 9) */
  49. #if defined (USE_SETCSMAP)
  50. #include <langinfo.h>
  51. #include <sys/param.h>
  52. #endif /* (USE_SETCSMAP) */
  53. #ifdef USE_SRIOCSREDIR
  54. #include <sys/strredir.h>
  55. #include <sys/stat.h>
  56. #endif /* USE_SRIOCSREDIR */
  57. #ifdef USE_TIOCCONS
  58. #ifdef IBM_ARCHITECTURE
  59. #include <sys/ioctl.h>
  60. #endif /* IBM_ARCHITECTURE */
  61. #include <sys/stat.h>
  62. #endif /* USE_TIOCCONS */
  63. #if defined(LINUX_ARCHITECTURE) || defined(CSRG_BASED)
  64. #include <sys/ioctl.h>
  65. #endif /* LINUX_ARCHITECTURE */
  66. #ifdef USE_STREAMS
  67. #include <sys/types.h>
  68. #include <stropts.h>
  69. #include <sys/conf.h>
  70. #endif /* USE_STREAMS */
  71. #if defined (USE_CSWIDTH)
  72. #include <sys/ioctl.h>
  73. #include <sys/eucioctl.h>
  74. #endif /* (USE_CSWIDTH) */
  75. #include <sys/wait.h>
  76. #include <ctype.h>
  77. #include <errno.h>
  78. #include <signal.h>
  79. #include <Xm/Xm.h>
  80. #define XTTYMODE_intr 0
  81. #define XTTYMODE_quit 1
  82. #define XTTYMODE_erase 2
  83. #define XTTYMODE_kill 3
  84. #define XTTYMODE_eof 4
  85. #define XTTYMODE_eol 5
  86. #define XTTYMODE_swtch 6
  87. #define XTTYMODE_start 7
  88. #define XTTYMODE_stop 8
  89. #define XTTYMODE_brk 9
  90. #define XTTYMODE_susp 10
  91. #define XTTYMODE_dsusp 11
  92. #define XTTYMODE_rprnt 12
  93. #define XTTYMODE_flush 13
  94. #define XTTYMODE_weras 14
  95. #define XTTYMODE_lnext 15
  96. #define NXTTYMODES 16
  97. #if defined(CSRG_BASED)
  98. #ifdef TAB3
  99. #undef TAB3
  100. #endif
  101. #ifdef TABDLY
  102. #undef TABDLY
  103. #endif
  104. #define TAB3 0x00000000
  105. #define NLDLY 0x00000000
  106. #define CRDLY 0x00000000
  107. #define TABDLY 0x00000000
  108. #define BSDLY 0x00000000
  109. #define VTDLY 0x00000000
  110. #define FFDLY 0x00000000
  111. #define CBAUD 0x00000000
  112. #endif
  113. typedef struct _ttyMode
  114. {
  115. char *name;
  116. int len;
  117. int set;
  118. char value;
  119. }
  120. ttyMode;
  121. ttyMode _DtTermPrimTtyModeList[] =
  122. {
  123. { "intr" , 4, 0, '\0' }, /* tchars.t_intrc ; VINTR */
  124. { "quit" , 4, 0, '\0' }, /* tchars.t_quitc ; VQUIT */
  125. { "erase", 5, 0, '\0' }, /* sgttyb.sg_erase ; VERASE */
  126. { "kill" , 4, 0, '\0' }, /* sgttyb.sg_kill ; VKILL */
  127. { "eof" , 3, 0, '\0' }, /* tchars.t_eofc ; VEOF */
  128. { "eol" , 3, 0, '\0' }, /* VEOL */
  129. { "swtch", 5, 0, '\0' }, /* VSWTCH */
  130. { "start", 5, 0, '\0' }, /* tchars.t_startc */
  131. { "stop" , 4, 0, '\0' }, /* tchars.t_stopc */
  132. { "brk" , 3, 0, '\0' }, /* tchars.t_brkc */
  133. { "susp" , 4, 0, '\0' }, /* ltchars.t_suspc */
  134. { "dsusp", 5, 0, '\0' }, /* ltchars.t_dsuspc */
  135. { "rprnt", 5, 0, '\0' }, /* ltchars.t_rprntc */
  136. { "flush", 5, 0, '\0' }, /* ltchars.t_flushc */
  137. { "weras", 5, 0, '\0' }, /* ltchars.t_werasc */
  138. { "lnext", 5, 0, '\0' }, /* ltchars.t_lnextc */
  139. { NULL, 0, 0, '\0' }, /* NULL terminate the array */
  140. };
  141. static int
  142. parseTtyModes
  143. (
  144. char *modeString,
  145. ttyMode *modeList
  146. )
  147. {
  148. ttyMode *pMode;
  149. int c;
  150. int modeCount = 0;
  151. /*
  152. ** Search to the end of the.
  153. */
  154. while (1) {
  155. /*
  156. ** Skip white space, if this is the end of the list,
  157. ** return.
  158. */
  159. while (*modeString && isascii(*modeString) && isspace(*modeString))
  160. {
  161. modeString++;
  162. }
  163. if (!*modeString)
  164. {
  165. DebugF('p', 2, fprintf(stderr,
  166. ">>parseTtyModes() hit end of mode string, return=%d\n",
  167. modeCount));
  168. return(modeCount);
  169. }
  170. /*
  171. ** Otherwise, see if 'modeString' is in the list of mode names.
  172. */
  173. for (pMode = modeList; pMode->name; pMode++)
  174. {
  175. DebugF('p', 2, fprintf(stderr,
  176. ">>parseTtyModes() comparing %.*s to %s\n",
  177. pMode->len, modeString, pMode->name));
  178. if (strncmp(modeString, pMode->name, pMode->len) == 0)
  179. {
  180. DebugF('p', 2, fprintf(stderr, ">>parseTtyModes() match!\n"));
  181. break;
  182. }
  183. }
  184. if (!pMode->name)
  185. {
  186. DebugF('p', 2, fprintf(stderr, ">>parseTtyModes() no match\n"));
  187. return(-1);
  188. }
  189. /*
  190. ** Now look for a value for the setting.
  191. ** (Skip white space, return an error if no value.)
  192. */
  193. modeString += pMode->len;
  194. while (*modeString && isascii(*modeString) && isspace(*modeString))
  195. {
  196. modeString++;
  197. }
  198. if (!*modeString)
  199. {
  200. DebugF('p', 2, fprintf(stderr,
  201. ">>parseTtyModes() missing value\n"));
  202. return(-1);
  203. }
  204. /*
  205. ** Make sure we handle control characters correctly.
  206. */
  207. if (*modeString == '^')
  208. {
  209. modeString++;
  210. /*
  211. ** keep control bits
  212. */
  213. c = ((*modeString == '?') ? 0177 : *modeString & 31);
  214. }
  215. else
  216. {
  217. c = *modeString;
  218. }
  219. /*
  220. ** Set the values, and get go back for more.
  221. */
  222. pMode->value = c;
  223. pMode->set = 1;
  224. modeCount++;
  225. modeString++;
  226. }
  227. /* return(modeCount); */
  228. }
  229. #if defined (USE_CSWIDTH)
  230. #define FIND_NUMBER(x, cp) \
  231. { \
  232. x = 0; \
  233. while (*cp && isdigit(*cp)) \
  234. { \
  235. x *= 10; \
  236. x += (*cp - '0'); \
  237. cp++; \
  238. } \
  239. }
  240. /*
  241. ** parse the cswidth string
  242. ** it should be in the form: X1[[:Y1][,X2[:Y2][,X3[:Y3]]]]
  243. */
  244. static void
  245. parseCSWidth
  246. (
  247. char *cp,
  248. eucioc_t *wp
  249. )
  250. {
  251. int x;
  252. int i;
  253. /*
  254. ** set all cs widths to 0
  255. */
  256. wp->eucw[1] = wp->eucw[2] = wp->eucw[3] = 0;
  257. wp->scrw[1] = wp->scrw[2] = wp->scrw[3] = 0;
  258. if (!cp)
  259. {
  260. return;
  261. }
  262. DebugF('p', 4, fprintf(stderr,
  263. ">>parseCSWidth(): csWidthString %s\n", cp));
  264. for (i = 1; i <= 3; i++)
  265. {
  266. /*
  267. ** read Xn
  268. */
  269. FIND_NUMBER(x, cp);
  270. wp->eucw[i] = x;
  271. if (!*cp)
  272. {
  273. wp->scrw[i] = wp->eucw[i];
  274. return;
  275. }
  276. /*
  277. ** Yn might exist
  278. */
  279. if (*cp == ':')
  280. {
  281. cp++;
  282. FIND_NUMBER(x, cp);
  283. wp->scrw[i] = x;
  284. if (!*cp)
  285. {
  286. return;
  287. }
  288. }
  289. else
  290. {
  291. wp->scrw[i] = wp->eucw[i];
  292. }
  293. cp++;
  294. }
  295. DebugF('p', 4, fprintf(stderr,"parseCSWidth():"));
  296. DebugF('p', 4, fprintf(stderr,
  297. " eucw[1] : %d, scrw[1] : %d\n", wp->eucw[1], wp->scrw[1]));
  298. DebugF('p', 4, fprintf(stderr,
  299. " eucw[2] : %d, scrw[2] : %d\n", wp->eucw[2], wp->scrw[2]));
  300. DebugF('p', 4, fprintf(stderr,
  301. " eucw[3] : %d, scrw[3] : %d\n", wp->eucw[3], wp->scrw[3]));
  302. }
  303. #endif /* (USE_CSWIDTH) */
  304. void _DtTermPrimPtySendBreak(int pty, int msec)
  305. {
  306. #if defined(USE_TIOCBREAK)
  307. (void) ioctl(pty, TIOCBREAK, 0);
  308. #elif defined(USE_TCSBRK)
  309. (void) ioctl(pty, TCSBRK, 0);
  310. #elif defined(USE_TCSENDBREAK)
  311. (void) tcsendbreak(pty, 0);
  312. #else /* none specified... */
  313. #error "There is no RS232 break code specified for this architecture. See TermPrimOSDepI.h for a list of #defines..."
  314. #endif /* rs232 break definition... */
  315. }
  316. void _DtTermPrimPtySetWindowSize(int pty, short pixelWidth, short pixelHeight,
  317. short characterRows, short characterColumns)
  318. {
  319. struct winsize ws;
  320. ws.ws_row = characterRows;
  321. ws.ws_col = characterColumns;
  322. ws.ws_xpixel = pixelWidth;
  323. ws.ws_ypixel = pixelHeight;
  324. (void) ioctl(pty, TIOCSWINSZ, &ws);
  325. }
  326. static struct termios refTio;
  327. static int refValid = 0;
  328. #if defined (USE_CSWIDTH)
  329. /*
  330. ** default width settings for ldterm
  331. */
  332. static eucioc_t refWp;
  333. #endif /* (USE_CSWIDTH) */
  334. void
  335. _DtTermPrimPtyGetDefaultModes(void)
  336. {
  337. int tty = -1;
  338. int refTty = -1;
  339. #if defined (USE_CSWIDTH)
  340. struct strioctl i_str;
  341. #endif /* (USE_CSWIDTH) */
  342. _DtTermProcessLock();
  343. if (!refValid) {
  344. /* see if we can get a reference tty to get our base reference from...
  345. */
  346. if ((tty = open("/dev/tty", O_RDONLY, 0)) >= 0) {
  347. if (!tcgetattr(tty, &refTio)) {
  348. /* we got a valid reference tty... */
  349. DebugF('p', 3, fprintf(stderr,
  350. ">>_DtTermPrimPtyGetDefaultModes() valid reference \"/dev/tty\"\n"));
  351. refValid = 1;
  352. }
  353. }
  354. if (!refValid) {
  355. for (refTty = 0; refTty < 3; refTty++) {
  356. if (!tcgetattr(refTty, &refTio)) {
  357. DebugF('p', 3, fprintf(stderr,
  358. ">>_DtTermPrimPtyGetDefaultModes() valid reference \fd %d\n", refTty));
  359. refValid = 1;
  360. break;
  361. }
  362. }
  363. }
  364. #if defined (USE_CSWIDTH)
  365. if (refValid && (MB_CUR_MAX > 1))
  366. {
  367. /*
  368. ** we are in a wide character locale, get the current
  369. ** width settings...
  370. */
  371. i_str.ic_cmd = EUC_WGET;
  372. i_str.ic_timout = 0;
  373. i_str.ic_len = sizeof(struct eucioc);
  374. i_str.ic_dp = (char *)&refWp;
  375. (void)ioctl(refTty, I_STR, &i_str);
  376. }
  377. #endif /* (USE_CSWIDTH) */
  378. /* all done...
  379. */
  380. /* close off the "/dev/tty" fd... */
  381. if (tty >= 0) {
  382. (void) close(tty);
  383. }
  384. }
  385. _DtTermProcessUnlock();
  386. }
  387. void
  388. _DtTermPrimPtyInit
  389. (
  390. int pty,
  391. char *modeString,
  392. char *csWidthString
  393. )
  394. {
  395. struct termios tio;
  396. #if defined (USE_CSWIDTH)
  397. struct strioctl i_str;
  398. eucioc_t wp;
  399. #endif /* (USE_CSWIDTH) */
  400. #if defined (USE_SETCSMAP)
  401. /*
  402. ** set thing up so we can use setcsmap()
  403. ** for the time being, this is IBM specific
  404. */
  405. char path[MAXPATHLEN];
  406. int oldStdin = -1;
  407. #endif /* (USE_SETCSMAP) */
  408. #ifdef NOTDEF
  409. #ifdef USE_STREAMS
  410. if (ioctl(pty, I_PUSH, "ptem") < 0) {
  411. (void) perror("I_PUSH ptem");
  412. }
  413. if (ioctl(pty, I_PUSH, "ldterm") < 0) {
  414. (void) perror("I_PUSH ldterm");
  415. }
  416. if (ioctl(pty, I_PUSH, "ttcompat") < 0) {
  417. (void) perror("I_PUSH ttcompat");
  418. }
  419. #endif /* USE_STREAMS */
  420. #endif /* NOTDEF */
  421. if (refValid) {
  422. /* we will start from the reference tty...
  423. */
  424. /* we already got the termios structure. No need to get again... */
  425. DebugF('p', 3, fprintf(stderr,
  426. ">>_DtTermPrimPtyInit() using refTio\n"));
  427. tio = refTio;
  428. #if defined (USE_CSWIDTH)
  429. /*
  430. ** use the cs width information from the reference...
  431. */
  432. wp = refWp;
  433. #endif /* (USE_CSWIDTH) */
  434. /* DKS: are there any other terminal states we need to get?... */
  435. } else {
  436. /* let's set a reasonable default... */
  437. DebugF('p', 3, fprintf(stderr,
  438. ">>_DtTermPrimPtyInit() generating default termio\n"));
  439. (void) memset(&tio, '\0', sizeof(tio));
  440. tio.c_iflag = ICRNL | IXON | IXOFF;
  441. tio.c_oflag = OPOST | ONLCR | TAB3;
  442. tio.c_cflag = B9600 | CS8 | CREAD | PARENB | HUPCL;
  443. tio.c_lflag = ISIG|ICANON|ECHO|ECHOE|ECHOK|IEXTEN|ECHOCTL|ECHOKE;
  444. /* DKS: this is termio specific. Do we need it?...
  445. tio.c_line = 0;
  446. */
  447. tio.c_cc[VINTR] = 0x7f; /* DEL */
  448. tio.c_cc[VQUIT] = '\\' & 0x3f; /* '^\' */
  449. tio.c_cc[VERASE] = '#'; /* '#' */
  450. tio.c_cc[VKILL] = '@'; /* '@' */
  451. tio.c_cc[VEOF] = 'D' & 0x3f; /* '^D' */
  452. tio.c_cc[VEOL] = '@' & 0x3f; /* '^@' */
  453. #ifdef VSWITCH
  454. tio.c_cc[VSWITCH] = '@' & 0x3f; /* '^@' */
  455. #endif /* VSWITCH */
  456. #if defined (USE_CSWIDTH)
  457. /*
  458. ** get the cs width information from the resource
  459. */
  460. parseCSWidth(csWidthString, &wp);
  461. #endif /* (USE_CSWIDTH) */
  462. }
  463. /* now, let's clean up certain flags... */
  464. /* input: nl->nl, don't ignore cr, cr->nl
  465. * turn on IXOFF pacing so that we can do paste without
  466. * overflowing the buffer...
  467. */
  468. tio.c_iflag &= ~(INLCR | IGNCR);
  469. tio.c_iflag |= ICRNL | IXOFF;
  470. /* output: cr->cr, nl is not return, no delays, nl->cr/nl
  471. */
  472. tio.c_oflag &= ~(OCRNL | ONLRET | NLDLY | CRDLY | TABDLY |
  473. BSDLY | VTDLY | FFDLY);
  474. tio.c_oflag |= ONLCR;
  475. /* baud rate is 9600 (nice default), turn off clocal and turn on
  476. * hupcl so that the last close will SIGHUP processes running on
  477. * the tty...
  478. */
  479. tio.c_cflag &= ~(CBAUD | CLOCAL);
  480. tio.c_cflag |= B9600 | HUPCL;
  481. /* enable signals, canonical processing (erase, kill, etc), echo...
  482. */
  483. tio.c_lflag |= ISIG | ICANON | ECHO | IEXTEN | ECHOCTL | ECHOKE;
  484. /* reset EOL to the default value (ksh mucks this up sometimes)...
  485. */
  486. tio.c_cc[VEOL] = '@' & 0x3f; /* '^@' */
  487. /* reset EOF to the default value (ksh and csh muck with this)... */
  488. tio.c_cc[VEOF] = 'D' & 0x3f; /* '^D' */
  489. /*
  490. ** Now its time to handle the ttyModes
  491. ** Decide if the user supplied a ttyModes resource, if so then
  492. ** parse it and if it was a legal mode string, pass the parse result
  493. */
  494. #define TMODE(ind,var) if (_DtTermPrimTtyModeList[ind].set) var = _DtTermPrimTtyModeList[ind].value;
  495. _DtTermProcessLock();
  496. if (modeString)
  497. {
  498. if (parseTtyModes(modeString, _DtTermPrimTtyModeList) < 0)
  499. {
  500. /*
  501. ** NOTE: should we prepend the program name to this string?
  502. */
  503. fprintf(stderr, "Bad tty modes \"%s\"\n", modeString);
  504. }
  505. else
  506. {
  507. TMODE (XTTYMODE_intr, tio.c_cc[VINTR]);
  508. TMODE (XTTYMODE_quit, tio.c_cc[VQUIT]);
  509. TMODE (XTTYMODE_erase, tio.c_cc[VERASE]);
  510. TMODE (XTTYMODE_kill, tio.c_cc[VKILL]);
  511. TMODE (XTTYMODE_eof, tio.c_cc[VEOF]);
  512. TMODE (XTTYMODE_eol, tio.c_cc[VEOL]);
  513. #if defined(HP_ARCHITECTURE)
  514. TMODE (XTTYMODE_swtch, tio.c_cc[VSWTCH]);
  515. TMODE (XTTYMODE_susp, tio.c_cc[VSUSP]);
  516. #if OSMAJORVERSION > 9
  517. /* HP-UX 10.0 supports the new, extended c_cc[] array...
  518. */
  519. TMODE (XTTYMODE_start, tio.c_cc[VSTART]);
  520. TMODE (XTTYMODE_stop, tio.c_cc[VSTOP]);
  521. TMODE (XTTYMODE_dsusp, tio.c_cc[VDSUSP]);
  522. #ifdef NOTDEF
  523. /* the following two parameters are not supported by
  524. * HP-UX 10.0.
  525. */
  526. TMODE (XTTYMODE_rprnt, tio.c_cc[VREPRINT]);
  527. TMODE (XTTYMODE_flush, tio.c_cc[VDISCARD]);
  528. #endif /* NOTDEF */
  529. TMODE (XTTYMODE_weras, tio.c_cc[VWERASE]);
  530. TMODE (XTTYMODE_lnext, tio.c_cc[VLNEXT]);
  531. #else /* OSMAJORVERSION > 9 */
  532. {
  533. /* With HP-UX 9.0 (and earlier) we need to set dsuspc
  534. * via the ltchars array. In addition, we have no support
  535. * for rprnt, flush, weras, and lnext...
  536. */
  537. struct ltchars ltc;
  538. if (!ioctl(pty, TIOCGLTC, &ltc)) {
  539. TMODE (XTTYMODE_dsusp, ltc.t_dsuspc);
  540. (void) ioctl(pty, TIOCSLTC, &ltc);
  541. }
  542. }
  543. #endif /* OSMAJORVERSION > 9 */
  544. #elif defined(IBM_ARCHITECTURE)
  545. TMODE (XTTYMODE_start, tio.c_cc[VSTRT]);
  546. TMODE (XTTYMODE_stop, tio.c_cc[VSTOP]);
  547. TMODE (XTTYMODE_susp, tio.c_cc[VSUSP]);
  548. TMODE (XTTYMODE_dsusp, tio.c_cc[VDSUSP]);
  549. TMODE (XTTYMODE_rprnt, tio.c_cc[VREPRINT]);
  550. TMODE (XTTYMODE_flush, tio.c_cc[VDISCRD]);
  551. TMODE (XTTYMODE_weras, tio.c_cc[VWERSE]);
  552. TMODE (XTTYMODE_lnext, tio.c_cc[VLNEXT]);
  553. #elif defined(SUN_ARCHITECTURE)
  554. TMODE (XTTYMODE_swtch, tio.c_cc[VSWTCH]);
  555. TMODE (XTTYMODE_start, tio.c_cc[VSTART]);
  556. TMODE (XTTYMODE_stop, tio.c_cc[VSTOP]);
  557. TMODE (XTTYMODE_susp, tio.c_cc[VSUSP]);
  558. TMODE (XTTYMODE_dsusp, tio.c_cc[VDSUSP]);
  559. TMODE (XTTYMODE_rprnt, tio.c_cc[VREPRINT]);
  560. TMODE (XTTYMODE_flush, tio.c_cc[VDISCARD]);
  561. TMODE (XTTYMODE_weras, tio.c_cc[VWERASE]);
  562. TMODE (XTTYMODE_lnext, tio.c_cc[VLNEXT]);
  563. #elif defined(ALPHA_ARCHITECTURE)
  564. TMODE (XTTYMODE_start, tio.c_cc[VSTART]);
  565. TMODE (XTTYMODE_stop, tio.c_cc[VSTOP]);
  566. TMODE (XTTYMODE_susp, tio.c_cc[VSUSP]);
  567. TMODE (XTTYMODE_dsusp, tio.c_cc[VDSUSP]);
  568. TMODE (XTTYMODE_rprnt, tio.c_cc[VREPRINT]);
  569. TMODE (XTTYMODE_flush, tio.c_cc[VDISCARD]);
  570. TMODE (XTTYMODE_weras, tio.c_cc[VWERASE]);
  571. TMODE (XTTYMODE_lnext, tio.c_cc[VLNEXT]);
  572. #endif
  573. }
  574. #undef TMODE
  575. }
  576. _DtTermProcessUnlock();
  577. (void) tcsetattr(pty, TCSADRAIN, &tio);
  578. #if defined (USE_CSWIDTH)
  579. if (MB_CUR_MAX > 1)
  580. {
  581. /*
  582. ** we are in a wide character locale, set the cs
  583. ** width settings...
  584. */
  585. i_str.ic_cmd = EUC_WSET;
  586. i_str.ic_timout = 0;
  587. i_str.ic_len = sizeof(struct eucioc);
  588. i_str.ic_dp = (char *)&wp;
  589. (void)ioctl(pty, I_STR, &i_str);
  590. }
  591. #endif /* (USE_CSWIDTH) */
  592. #if defined (USE_SETCSMAP)
  593. /*
  594. ** NOTE:
  595. ** Setcsmap() only operates on STDIN, so we have to do some
  596. ** munging around to map the pty to STDIN in order to get
  597. ** the desired result. This may seem wasteful, but it
  598. ** makes it easier to encapsulate the OS dependencies in
  599. ** this function.
  600. */
  601. if (pty != 0)
  602. {
  603. oldStdin = fcntl(0, F_DUPFD, 1);
  604. (void) close(0);
  605. (void) dup(pty);
  606. }
  607. sprintf(path, "%s%s", CSMAP_DIR, nl_langinfo(CODESET));
  608. if(access(path, E_ACC|R_ACC) == 0)
  609. {
  610. setcsmap(path);
  611. }
  612. if (pty != 0)
  613. {
  614. (void) close(0);
  615. if (oldStdin >= 0)
  616. {
  617. (void) dup(oldStdin);
  618. (void) close(oldStdin);
  619. }
  620. }
  621. #endif /* (USE_SETCSMAP) */
  622. }
  623. #if defined(USE_TIOCCONS)
  624. #ifndef CONSOLE_DEVICE
  625. #define CONSOLE_DEVICE "/dev/console"
  626. #endif /* CONSOLE_DEVICE */
  627. void _DtTermPrimPtyConsoleModeEnable(int pty)
  628. {
  629. struct stat st;
  630. int one = 1;
  631. /* check to see if we are the owner of the device... */
  632. if (!stat(CONSOLE_DEVICE, &st)) {
  633. /* stat succeeded... */
  634. if (st.st_uid == getuid()) {
  635. /* we are the owner, check the access... */
  636. if (!access(CONSOLE_DEVICE, R_OK | W_OK)) {
  637. /* and we can read/write it... */
  638. /* we need to be setuid root... */
  639. (void) _DtTermPrimToggleSuidRoot(True);
  640. if (ioctl(pty, TIOCCONS, &one)) {
  641. /* failure, errno was set... */
  642. (void) perror(CONSOLE_DEVICE);
  643. (void) fprintf(stderr,
  644. "attempt to make tty the console failed\n");
  645. }
  646. /* we no longer need to be suid root... */
  647. (void) _DtTermPrimToggleSuidRoot(False);
  648. } else {
  649. /* we can't read/write it... */
  650. (void) perror(CONSOLE_DEVICE);
  651. (void) fprintf(stderr, "-C console access denied\n");
  652. }
  653. } else {
  654. /* we are not the owner -- return an access owner... */
  655. errno = EACCES;
  656. (void) perror(CONSOLE_DEVICE);
  657. (void) fprintf(stderr, "-C console access denied\n");
  658. }
  659. } else {
  660. /* we were unable to stat the file, errno is already set,
  661. * failure...
  662. */
  663. (void) perror(CONSOLE_DEVICE);
  664. (void) fprintf(stderr, "-C console access denied\n");
  665. }
  666. }
  667. #elif defined(USE_SRIOCSREDIR)
  668. #ifndef CONSOLE_DEVICE
  669. #define CONSOLE_DEVICE "/dev/console"
  670. #endif /* CONSOLE_DEVICE */
  671. void _DtTermPrimPtyConsoleModeEnable(int pty)
  672. {
  673. struct stat st;
  674. int consoleFd;
  675. /* check to see if we are the owner of the device... */
  676. if (!stat(CONSOLE_DEVICE, &st)) {
  677. /* stat succeeded... */
  678. if (st.st_uid == getuid()) {
  679. /* we are the owner, open the file... */
  680. if ((consoleFd = open("/dev/console", O_RDWR | O_NOCTTY)) >= 0) {
  681. if (ioctl(consoleFd, SRIOCSREDIR, pty) == -1) {
  682. (void) perror(CONSOLE_DEVICE);
  683. (void) fprintf(stderr,
  684. "attempt to make tty the console failed\n");
  685. }
  686. (void) close(consoleFd);
  687. } else {
  688. /* we can't open it for reading and writing... */
  689. (void) perror(CONSOLE_DEVICE);
  690. (void) fprintf(stderr, "-C console access denied\n");
  691. }
  692. } else {
  693. /* we are not the owner -- return an access owner... */
  694. errno = EACCES;
  695. (void) perror(CONSOLE_DEVICE);
  696. (void) fprintf(stderr, "-C console access denied\n");
  697. }
  698. } else {
  699. /* we were unable to stat the file, errno is already set,
  700. * failure...
  701. */
  702. (void) perror(CONSOLE_DEVICE);
  703. (void) fprintf(stderr, "-C console access denied\n");
  704. }
  705. }
  706. #else
  707. void _DtTermPrimPtyConsoleModeEnable(int pty)
  708. {
  709. (void) fprintf(stderr,
  710. "-C console access not supported on this architecture\n");
  711. }
  712. #endif