X-Git-Url: https://asedeno.scripts.mit.edu/gitweb/?a=blobdiff_plain;f=unix%2Fuxpty.c;h=39f96f126afd9a347f3c46caf2bd7c8fed914015;hb=095072fa46b2d7b8beafaddb2f873d2f500a1e10;hp=33cc2c1e702d4e87574f917a75500bfe19d117ae;hpb=7658b291dbde482d483500883af8ae31c4194e8c;p=PuTTY.git diff --git a/unix/uxpty.c b/unix/uxpty.c index 33cc2c1e..39f96f12 100644 --- a/unix/uxpty.c +++ b/unix/uxpty.c @@ -180,6 +180,8 @@ static struct utmpx utmp_entry; */ char **pty_argv; +char *pty_osx_envrestore_prefix; + static void pty_close(Pty pty); static void pty_try_write(Pty pty); @@ -763,18 +765,6 @@ static const char *pty_init(void *frontend, void **backend_handle, Conf *conf, if (pty->master_fd < 0) pty_open_master(pty); - /* - * Set the backspace character to be whichever of ^H and ^? is - * specified by bksp_is_delete. - */ - { - struct termios attrs; - tcgetattr(pty->master_fd, &attrs); - attrs.c_cc[VERASE] = conf_get_int(conf, CONF_bksp_is_delete) - ? '\177' : '\010'; - tcsetattr(pty->master_fd, TCSANOW, &attrs); - } - #ifndef OMIT_UTMP /* * Stamp utmp (that is, tell the utmp helper process to do so), @@ -815,10 +805,40 @@ static const char *pty_init(void *frontend, void **backend_handle, Conf *conf, } if (pid == 0) { + struct termios attrs; + /* * We are the child. */ + if (pty_osx_envrestore_prefix) { + int plen = strlen(pty_osx_envrestore_prefix); + extern char **environ; + char **ep; + + restart_osx_env_restore: + for (ep = environ; *ep; ep++) { + char *e = *ep; + + if (!strncmp(e, pty_osx_envrestore_prefix, plen)) { + int unset = (e[plen] == 'u'); + char *pname = dupprintf("%.*s", (int)strcspn(e, "="), e); + char *name = pname + plen + 1; + char *value = e + strcspn(e, "="); + if (*value) value++; + value = dupstr(value); + if (unset) + unsetenv(name); + else + setenv(name, value, 1); + unsetenv(pname); + sfree(pname); + sfree(value); + goto restart_osx_env_restore; + } + } + } + slavefd = pty_open_slave(pty); if (slavefd < 0) { perror("slave pty: open"); @@ -837,6 +857,34 @@ static const char *pty_init(void *frontend, void **backend_handle, Conf *conf, #endif pgrp = getpid(); tcsetpgrp(0, pgrp); + + /* + * Set up configuration-dependent termios settings on the new + * pty. Linux would have let us do this on the pty master + * before we forked, but that fails on OS X, so we do it here + * instead. + */ + if (tcgetattr(0, &attrs) == 0) { + /* + * Set the backspace character to be whichever of ^H and + * ^? is specified by bksp_is_delete. + */ + attrs.c_cc[VERASE] = conf_get_int(conf, CONF_bksp_is_delete) + ? '\177' : '\010'; + + /* + * Set the IUTF8 bit iff the character set is UTF-8. + */ +#ifdef IUTF8 + if (frontend_is_utf8(frontend)) + attrs.c_iflag |= IUTF8; + else + attrs.c_iflag &= ~IUTF8; +#endif + + tcsetattr(0, TCSANOW, &attrs); + } + setpgid(pgrp, pgrp); { int ptyfd = open(pty->name, O_WRONLY, 0); @@ -894,14 +942,14 @@ static const char *pty_init(void *frontend, void **backend_handle, Conf *conf, /* * SIGINT, SIGQUIT and SIGPIPE may have been set to ignored by * our parent, particularly by things like sh -c 'pterm &' and - * some window or session managers. SIGCHLD, meanwhile, was - * blocked during pt_main() startup. Reverse all this for our - * child process. + * some window or session managers. SIGPIPE was also + * (potentially) blocked by us during startup. Reverse all + * this for our child process. */ putty_signal(SIGINT, SIG_DFL); putty_signal(SIGQUIT, SIG_DFL); putty_signal(SIGPIPE, SIG_DFL); - block_signal(SIGCHLD, 0); + block_signal(SIGPIPE, 0); if (pty_argv) { /* * Exec the exact argument list we were given. @@ -1200,6 +1248,7 @@ Backend pty_backend = { pty_provide_logctx, pty_unthrottle, pty_cfg_info, + NULL /* test_for_upstream */, "pty", -1, 0