summaryrefslogtreecommitdiff
path: root/sshd.c
diff options
context:
space:
mode:
authorDamien Miller <djm@mindrot.org>2000-03-02 23:30:53 +1100
committerDamien Miller <djm@mindrot.org>2000-03-02 23:30:53 +1100
commitc7d8dbbb0dfdeb3f854d58c9bf084db2b72ded77 (patch)
treec3a6eec5473e66ea866bdfd3aa4055325eb63177 /sshd.c
parenta22ba0152cebff060be2de75ce2ab52a2442ea73 (diff)
- Applied pty cleanup patch from markus.friedl@informatik.uni-erlangen.de
Diffstat (limited to 'sshd.c')
-rw-r--r--sshd.c102
1 files changed, 47 insertions, 55 deletions
diff --git a/sshd.c b/sshd.c
index 0a6045e7f..f49b45368 100644
--- a/sshd.c
+++ b/sshd.c
@@ -1622,6 +1622,37 @@ xauthfile_cleanup_proc(void *ignore)
1622 } 1622 }
1623} 1623}
1624 1624
1625struct pty_cleanup_context {
1626 const char *ttyname;
1627 int pid;
1628};
1629
1630/*
1631 * Function to perform cleanup if we get aborted abnormally (e.g., due to a
1632 * dropped connection).
1633 */
1634void
1635pty_cleanup_proc(void *context)
1636{
1637 struct pty_cleanup_context *cu = context;
1638
1639 debug("pty_cleanup_proc called");
1640
1641 /* Record that the user has logged out. */
1642 record_logout(cu->pid, cu->ttyname);
1643
1644 /* Release the pseudo-tty. */
1645 pty_release(cu->ttyname);
1646}
1647
1648/* simple cleanup: chown tty slave back to root */
1649static void
1650pty_release_proc(void *tty)
1651{
1652 char *ttyname = tty;
1653 pty_release(ttyname);
1654}
1655
1625/* 1656/*
1626 * Prepares for an interactive session. This is called after the user has 1657 * Prepares for an interactive session. This is called after the user has
1627 * been successfully authenticated. During this message exchange, pseudo 1658 * been successfully authenticated. During this message exchange, pseudo
@@ -1636,11 +1667,7 @@ do_authenticated(struct passwd * pw)
1636 int have_pty = 0, ptyfd = -1, ttyfd = -1, xauthfd = -1; 1667 int have_pty = 0, ptyfd = -1, ttyfd = -1, xauthfd = -1;
1637 int row, col, xpixel, ypixel, screen; 1668 int row, col, xpixel, ypixel, screen;
1638 char ttyname[64]; 1669 char ttyname[64];
1639 char *command, *term = NULL, *display = NULL, *proto = NULL, 1670 char *command, *term = NULL, *display = NULL, *proto = NULL, *data = NULL;
1640 *data = NULL;
1641 struct group *grp;
1642 gid_t tty_gid;
1643 mode_t tty_mode;
1644 int n_bytes; 1671 int n_bytes;
1645 1672
1646 /* 1673 /*
@@ -1698,33 +1725,20 @@ do_authenticated(struct passwd * pw)
1698 error("Failed to allocate pty."); 1725 error("Failed to allocate pty.");
1699 goto fail; 1726 goto fail;
1700 } 1727 }
1701 /* Determine the group to make the owner of the tty. */ 1728 fatal_add_cleanup(pty_release_proc, (void *)ttyname);
1702 grp = getgrnam("tty"); 1729 pty_setowner(pw, ttyname);
1703 if (grp) {
1704 tty_gid = grp->gr_gid;
1705 tty_mode = S_IRUSR | S_IWUSR | S_IWGRP;
1706 } else {
1707 tty_gid = pw->pw_gid;
1708 tty_mode = S_IRUSR | S_IWUSR | S_IWGRP | S_IWOTH;
1709 }
1710
1711 /* Change ownership of the tty. */
1712 if (chown(ttyname, pw->pw_uid, tty_gid) < 0)
1713 fatal("chown(%.100s, %d, %d) failed: %.100s",
1714 ttyname, pw->pw_uid, tty_gid, strerror(errno));
1715 if (chmod(ttyname, tty_mode) < 0)
1716 fatal("chmod(%.100s, 0%o) failed: %.100s",
1717 ttyname, tty_mode, strerror(errno));
1718 1730
1719 /* Get TERM from the packet. Note that the value may be of arbitrary length. */ 1731 /* Get TERM from the packet. Note that the value may be of arbitrary length. */
1720 term = packet_get_string(&dlen); 1732 term = packet_get_string(&dlen);
1721 packet_integrity_check(dlen, strlen(term), type); 1733 packet_integrity_check(dlen, strlen(term), type);
1722 /* packet_integrity_check(plen, 4 + dlen + 4*4 + n_bytes, type); */ 1734
1723 /* Remaining bytes */ 1735 /* Remaining bytes */
1724 n_bytes = plen - (4 + dlen + 4 * 4); 1736 n_bytes = plen - (4 + dlen + 4 * 4);
1725 1737
1726 if (strcmp(term, "") == 0) 1738 if (strcmp(term, "") == 0) {
1739 xfree(term);
1727 term = NULL; 1740 term = NULL;
1741 }
1728 1742
1729 /* Get window size from the packet. */ 1743 /* Get window size from the packet. */
1730 row = packet_get_int(); 1744 row = packet_get_int();
@@ -1998,29 +2012,6 @@ do_exec_no_pty(const char *command, struct passwd * pw,
1998#endif /* USE_PIPES */ 2012#endif /* USE_PIPES */
1999} 2013}
2000 2014
2001struct pty_cleanup_context {
2002 const char *ttyname;
2003 int pid;
2004};
2005
2006/*
2007 * Function to perform cleanup if we get aborted abnormally (e.g., due to a
2008 * dropped connection).
2009 */
2010void
2011pty_cleanup_proc(void *context)
2012{
2013 struct pty_cleanup_context *cu = context;
2014
2015 debug("pty_cleanup_proc called");
2016
2017 /* Record that the user has logged out. */
2018 record_logout(cu->pid, cu->ttyname);
2019
2020 /* Release the pseudo-tty. */
2021 pty_release(cu->ttyname);
2022}
2023
2024/* 2015/*
2025 * This is called to fork and execute a command when we have a tty. This 2016 * This is called to fork and execute a command when we have a tty. This
2026 * will call do_child from the child, and server_loop from the parent after 2017 * will call do_child from the child, and server_loop from the parent after
@@ -2167,6 +2158,15 @@ do_exec_pty(const char *command, int ptyfd, int ttyfd,
2167 close(ttyfd); 2158 close(ttyfd);
2168 2159
2169 /* 2160 /*
2161 * Add a cleanup function to clear the utmp entry and record logout
2162 * time in case we call fatal() (e.g., the connection gets closed).
2163 */
2164 cleanup_context.pid = pid;
2165 cleanup_context.ttyname = ttyname;
2166 fatal_add_cleanup(pty_cleanup_proc, (void *) &cleanup_context);
2167 fatal_remove_cleanup(pty_release_proc, (void *) ttyname);
2168
2169 /*
2170 * Create another descriptor of the pty master side for use as the 2170 * Create another descriptor of the pty master side for use as the
2171 * standard input. We could use the original descriptor, but this 2171 * standard input. We could use the original descriptor, but this
2172 * simplifies code in server_loop. The descriptor is bidirectional. 2172 * simplifies code in server_loop. The descriptor is bidirectional.
@@ -2175,14 +2175,6 @@ do_exec_pty(const char *command, int ptyfd, int ttyfd,
2175 if (fdout < 0) 2175 if (fdout < 0)
2176 packet_disconnect("dup failed: %.100s", strerror(errno)); 2176 packet_disconnect("dup failed: %.100s", strerror(errno));
2177 2177
2178 /*
2179 * Add a cleanup function to clear the utmp entry and record logout
2180 * time in case we call fatal() (e.g., the connection gets closed).
2181 */
2182 cleanup_context.pid = pid;
2183 cleanup_context.ttyname = ttyname;
2184 fatal_add_cleanup(pty_cleanup_proc, (void *) &cleanup_context);
2185
2186 /* Enter interactive session. */ 2178 /* Enter interactive session. */
2187 server_loop(pid, ptyfd, fdout, -1); 2179 server_loop(pid, ptyfd, fdout, -1);
2188 /* server_loop has not closed ptyfd and fdout. */ 2180 /* server_loop has not closed ptyfd and fdout. */