home *** CD-ROM | disk | FTP | other *** search
/ The Hacker's Encyclopedia 1998 / hackers_encyclopedia.iso / hacking / unix / freebsds.txt < prev    next >
Encoding:
PGP Message  |  2003-06-11  |  12.5 KB  |  359 lines

  1. -----BEGIN PGP SIGNED MESSAGE-----
  2.  
  3. =============================================================================
  4. FreeBSD-SA-96:21                                            Security Advisory
  5.                                                                 FreeBSD, Inc.
  6.  
  7. Topic:          unauthorized access via buffer overrun in talkd
  8.  
  9. Category:       core
  10. Module:         talkd
  11. Announced:      1997-01-18
  12. Affects:        1.0, 1.1, 2.1.0, 2.1.5, 2.1.6, 2.1.6.1
  13. Corrected:      2.2-current as of 1997-01-18
  14.                 2.1-stable  as of 1197-01-18
  15. FreeBSD only:   no
  16.  
  17. Patches:        ftp://freebsd.org/pub/CERT/patches/SA-96:21/
  18. References:     AUSCERT AA-97.01 (Australian CERT organization),
  19.                 SEI CERT VU#5942 (internal tracking reference only)
  20.  
  21. =============================================================================
  22.  
  23. I.   Background
  24.  
  25.      Buffer overrun (aka stack overflow) exploits in system
  26.      supplied and locally installed utilities are commonly
  27.      used by individuals wishing to obtain unauthorized access to
  28.      computer systems.  The FreeBSD team has been reviewing and
  29.      fixing the source code pool to eliminate potential exploits
  30.      based on this technique.
  31.  
  32.      Recently, the Australian CERT organization received information
  33.      of a buffer-overrun vulnerability in the talkd daemon shipped in
  34.      most modern BSD based systems.
  35.  
  36.  
  37. II.  Problem Description
  38.  
  39.      To quote AUSCERT:
  40.  
  41.         talk is a communication program which copies text from one
  42.         users terminal to that of another, possibly remote, user.
  43.         talkd is the daemon that notifies a user that someone else wishes
  44.         to initiate a conversation.
  45.  
  46.         As part of the talk connection, talkd does a DNS lookup
  47.         for the hostname of the host where the connection is being
  48.         initiating from.  Due to insufficient bounds checking on
  49.         the buffer where the hostname is stored, it is possible to
  50.         overwrite the internal stack space of talkd.  By carefully
  51.         manipulating the hostname information, it is possible to
  52.         force talkd to execute arbitrary commands.  As talkd runs
  53.         with root privileges, this may allow intruders to remotely
  54.         execute arbitrary commands with these privileges.
  55.  
  56.         This attack requires an intruder to be able to make a
  57.         network connection to a vulnerable talkd program and provide
  58.         corrupt DNS information to that host.
  59.  
  60.         This type of attack is a particular instance of the problem
  61.         described in CERT advisory CA-96.04 "Corrupt Information
  62.         from Network Servers".  This advisory is available from:
  63.  
  64.                 ftp://info.cert.org/pub/cert_advisories/
  65.  
  66.      Recent versions of FreeBSD 2.2 -current may not be affected
  67.      with this vulnerability due to improved security in
  68.      new versions of BIND, which sanity-check the results of
  69.      reverse name lookups performed by the DNS system.
  70.  
  71.  
  72. III. Impact
  73.  
  74.  
  75.      Intruders may be able to remotely execute arbitrary commands
  76.      with root privileges.
  77.  
  78.      Access to a valid user account on the local system is not
  79.      required.
  80.  
  81.  
  82. IV. Workaround
  83.  
  84.      Disable the ntalkd program found in /etc/inetd.conf by
  85.      commenting the appropriate line out and reconfiguring inetd.
  86.  
  87.      # grep -i ntalk /etc/inetd.conf
  88.      ntalk   dgram   udp     wait    root    /usr/libexec/ntalkd     ntalkd
  89.  
  90.      After editing /etc/inetd.conf, reconfigure inetd by sending
  91.      it a HUP signal.
  92.  
  93.      # kill -HUP `cat /var/run/inetd.pid`
  94.  
  95. V. Solution
  96.  
  97.      The patches found at the following URL fix this vulnerability.
  98.      Patches are available for FreeBSD 2.1.x (-stable) and -current.
  99.  
  100.      Acknowledgment:
  101.  
  102.          These patches were based off of published work provided by
  103.          BSDI, Inc.
  104.  
  105.      After applying these patches, recompile and re-install the
  106.      affected utilities.
  107.  
  108.      For FreeBSD -current (2.2 prerelease and 3.0 prerelease)
  109.      systems:
  110.  
  111.     Index: announce.c
  112.     ===================================================================
  113.     RCS file: /cvs/freebsd/src/libexec/talkd/announce.c,v
  114.     retrieving revision 1.6
  115.     diff -u -r1.6 announce.c
  116.     --- announce.c      1997/01/14 06:20:58     1.6
  117.     +++ announce.c      1997/01/18 08:27:04
  118.     @@ -34,7 +34,7 @@
  119.       */
  120.  
  121.      #ifndef lint
  122.     -static char sccsid[] = "@(#)announce.c     8.2 (Berkeley) 1/7/94";
  123.     +static char sccsid[] = "@(#)announce.c     8.3 (Berkeley) 4/28/95";
  124.      #endif /* not lint */
  125.  
  126.      #include <sys/types.h>
  127.     @@ -43,13 +43,17 @@
  128.      #include <sys/time.h>
  129.      #include <sys/wait.h>
  130.      #include <sys/socket.h>
  131.     +
  132.      #include <protocols/talkd.h>
  133.     +
  134.      #include <errno.h>
  135.     -#include <syslog.h>
  136.     -#include <unistd.h>
  137.     +#include <paths.h>
  138.      #include <stdio.h>
  139.     +#include <stdlib.h>
  140.      #include <string.h>
  141.     -#include <paths.h>
  142.     +#include <syslog.h>
  143.     +#include <unistd.h>
  144.     +#include <vis.h>
  145.  
  146.      extern char hostname[];
  147.  
  148.     @@ -78,7 +82,7 @@
  149.  
  150.      #define max(a,b) ( (a) > (b) ? (a) : (b) )
  151.      #define N_LINES 5
  152.     -#define N_CHARS 120
  153.     +#define N_CHARS 256
  154.  
  155.      /*
  156.       * Build a block of characters containing the message.
  157.     @@ -100,33 +104,37 @@
  158.             char line_buf[N_LINES][N_CHARS];
  159.             int sizes[N_LINES];
  160.             char big_buf[N_LINES*N_CHARS];
  161.     -   char *bptr, *lptr, *ttymsg();
  162.     +   char *bptr, *lptr, *vis_user;
  163.             int i, j, max_size;
  164.  
  165.             i = 0;
  166.             max_size = 0;
  167.             gettimeofday(&clock, &zone);
  168.             localclock = localtime( &clock.tv_sec );
  169.     -   (void)sprintf(line_buf[i], " ");
  170.     +   (void)snprintf(line_buf[i], N_CHARS, " ");
  171.             sizes[i] = strlen(line_buf[i]);
  172.             max_size = max(max_size, sizes[i]);
  173.             i++;
  174.     -   (void)sprintf(line_buf[i], "Message from Talk_Daemon@%s at %d:%02d ...",
  175.     -   hostname, localclock->tm_hour , localclock->tm_min );
  176.     +   (void)snprintf(line_buf[i], N_CHARS,
  177.     +           "Message from Talk_Daemon@%s at %d:%02d ...",
  178.     +           hostname, localclock->tm_hour , localclock->tm_min );
  179.             sizes[i] = strlen(line_buf[i]);
  180.             max_size = max(max_size, sizes[i]);
  181.             i++;
  182.     -   (void)sprintf(line_buf[i], "talk: connection requested by %s@%s",
  183.     -           request->l_name, remote_machine);
  184.     +
  185.     +   vis_user = malloc(strlen(request->l_name) * 4 + 1);
  186.     +   strvis(vis_user, request->l_name, VIS_CSTYLE);
  187.     +   (void)snprintf(line_buf[i], N_CHARS,
  188.     +       "talk: connection requested by %s@%s", vis_user, remote_machine);
  189.             sizes[i] = strlen(line_buf[i]);
  190.             max_size = max(max_size, sizes[i]);
  191.             i++;
  192.     -   (void)sprintf(line_buf[i], "talk: respond with:  talk %s@%s",
  193.     -           request->l_name, remote_machine);
  194.     +   (void)snprintf(line_buf[i], N_CHARS, "talk: respond with:  talk %s@%s",
  195.     +       vis_user, remote_machine);
  196.             sizes[i] = strlen(line_buf[i]);
  197.             max_size = max(max_size, sizes[i]);
  198.             i++;
  199.     -   (void)sprintf(line_buf[i], " ");
  200.     +   (void)snprintf(line_buf[i], N_CHARS, " ");
  201.             sizes[i] = strlen(line_buf[i]);
  202.             max_size = max(max_size, sizes[i]);
  203.             i++;
  204.     Index: talkd.c
  205.     ===================================================================
  206.     RCS file: /cvs/freebsd/src/libexec/talkd/talkd.c,v
  207.     retrieving revision 1.5
  208.     diff -u -r1.5 talkd.c
  209.     --- talkd.c 1997/01/14 06:21:01     1.5
  210.     +++ talkd.c 1997/01/18 08:26:44
  211.     @@ -71,7 +71,7 @@
  212.      void       timeout();
  213.      long       lastmsgtime;
  214.  
  215.     -char    hostname[MAXHOSTNAMELEN];
  216.     +char    hostname[MAXHOSTNAMELEN + 1];
  217.  
  218.      #define TIMEOUT 30
  219.      #define MAXIDLE 120
  220.  
  221.     For FreeBSD 2.1 based systems:
  222.  
  223.     --- announce.c      1995/05/30 05:46:38     1.3
  224.     +++ announce.c      1997/01/18 08:33:55     1.3.4.1
  225.     @@ -32,7 +32,7 @@
  226.       */
  227.  
  228.      #ifndef lint
  229.     -static char sccsid[] = "@(#)announce.c     8.2 (Berkeley) 1/7/94";
  230.     +static char sccsid[] = "@(#)announce.c     8.3 (Berkeley) 4/28/95";
  231.      #endif /* not lint */
  232.  
  233.      #include <sys/types.h>
  234.     @@ -41,15 +41,18 @@
  235.      #include <sys/time.h>
  236.      #include <sys/wait.h>
  237.      #include <sys/socket.h>
  238.     +
  239.      #include <protocols/talkd.h>
  240.     -#include <sgtty.h>
  241.     +
  242.      #include <errno.h>
  243.     -#include <syslog.h>
  244.     -#include <unistd.h>
  245.     +#include <paths.h>
  246.      #include <stdio.h>
  247.     +#include <stdlib.h>
  248.      #include <string.h>
  249.     -#include <paths.h>
  250.     -
  251.     +#include <syslog.h>
  252.     +#include <unistd.h>
  253.     +#include <vis.h>
  254.     +
  255.      extern char hostname[];
  256.  
  257.      /*
  258.     @@ -77,7 +80,7 @@
  259.  
  260.      #define max(a,b) ( (a) > (b) ? (a) : (b) )
  261.      #define N_LINES 5
  262.     -#define N_CHARS 120
  263.     +#define N_CHARS 256
  264.  
  265.      /*
  266.       * Build a block of characters containing the message.
  267.     @@ -99,33 +102,37 @@
  268.             char line_buf[N_LINES][N_CHARS];
  269.             int sizes[N_LINES];
  270.             char big_buf[N_LINES*N_CHARS];
  271.     -   char *bptr, *lptr, *ttymsg();
  272.     +   char *bptr, *lptr, *vis_user;
  273.             int i, j, max_size;
  274.  
  275.             i = 0;
  276.             max_size = 0;
  277.             gettimeofday(&clock, &zone);
  278.             localclock = localtime( &clock.tv_sec );
  279.     -   (void)sprintf(line_buf[i], " ");
  280.     +   (void)snprintf(line_buf[i], N_CHARS, " ");
  281.             sizes[i] = strlen(line_buf[i]);
  282.             max_size = max(max_size, sizes[i]);
  283.             i++;
  284.     -   (void)sprintf(line_buf[i], "Message from Talk_Daemon@%s at %d:%02d ...",
  285.     -   hostname, localclock->tm_hour , localclock->tm_min );
  286.     +   (void)snprintf(line_buf[i], N_CHARS,
  287.     +           "Message from Talk_Daemon@%s at %d:%02d ...",
  288.     +           hostname, localclock->tm_hour , localclock->tm_min );
  289.             sizes[i] = strlen(line_buf[i]);
  290.             max_size = max(max_size, sizes[i]);
  291.             i++;
  292.     -   (void)sprintf(line_buf[i], "talk: connection requested by %s@%s",
  293.     -           request->l_name, remote_machine);
  294.     +
  295.     +   vis_user = malloc(strlen(request->l_name) * 4 + 1);
  296.     +   strvis(vis_user, request->l_name, VIS_CSTYLE);
  297.     +   (void)snprintf(line_buf[i], N_CHARS,
  298.     +       "talk: connection requested by %s@%s", vis_user, remote_machine);
  299.             sizes[i] = strlen(line_buf[i]);
  300.             max_size = max(max_size, sizes[i]);
  301.             i++;
  302.     -   (void)sprintf(line_buf[i], "talk: respond with:  talk %s@%s",
  303.     -           request->l_name, remote_machine);
  304.     +   (void)snprintf(line_buf[i], N_CHARS, "talk: respond with:  talk %s@%s",
  305.     +       vis_user, remote_machine);
  306.             sizes[i] = strlen(line_buf[i]);
  307.             max_size = max(max_size, sizes[i]);
  308.             i++;
  309.     -   (void)sprintf(line_buf[i], " ");
  310.     +   (void)snprintf(line_buf[i], N_CHARS, " ");
  311.             sizes[i] = strlen(line_buf[i]);
  312.             max_size = max(max_size, sizes[i]);
  313.             i++;
  314.     Index: talkd.c
  315.     ===================================================================
  316.     RCS file: /home/ncvs/src/libexec/talkd/talkd.c,v
  317.     retrieving revision 1.3
  318.     retrieving revision 1.3.4.1
  319.     diff -u -r1.3 -r1.3.4.1
  320.     --- talkd.c 1995/05/30 05:46:44     1.3
  321.     +++ talkd.c 1997/01/18 08:33:56     1.3.4.1
  322.     @@ -69,7 +69,7 @@
  323.      void       timeout();
  324.      long       lastmsgtime;
  325.  
  326.     -char    hostname[MAXHOSTNAMELEN];
  327.     +char    hostname[MAXHOSTNAMELEN + 1];
  328.  
  329.      #define TIMEOUT 30
  330.      #define MAXIDLE 120
  331.  
  332.  
  333. =============================================================================
  334. FreeBSD, Inc.
  335.  
  336. Web Site:                       http://www.freebsd.org/
  337. Confidential contacts:          security-officer@freebsd.org
  338. PGP Key:                        ftp://freebsd.org/pub/CERT/public_key.asc
  339. Security notifications:         security-notifications@freebsd.org
  340. Security public discussion:     security@freebsd.org
  341.  
  342. Notice: Any patches in this document may not apply cleanly due to
  343.         modifications caused by digital signature or mailer software.
  344.         Please reference the URL listed at the top of this document
  345.         for original copies of all patches if necessary.
  346. =============================================================================
  347.  
  348. -----BEGIN PGP SIGNATURE-----
  349. Version: 2.6.3ia
  350. Charset: noconv
  351.  
  352. iQCVAwUBMuCVAVUuHi5z0oilAQGx7gQAiiptKNx7xoeHec1jmBFLsoGBrxO9H3TC
  353. 0FHl4n3p/MQEO3OEfChepC5coTAe00SjOEpnAZIinHbtVzNaodPs0hyMbQ7UnpPq
  354. wIRlxsPhxVuS+rbrY62pvn1Iagr4SaMAaseGK18f+Tq2Lbwc6//1bTOBn+Ms980F
  355. VaXsIaKYinQ=
  356. =yj1H
  357. -----END PGP SIGNATURE-----
  358.  
  359.