emacs-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Emacs-diffs] /srv/bzr/emacs/trunk r107564: Don't access freed memory in


From: Andreas Schwab
Subject: [Emacs-diffs] /srv/bzr/emacs/trunk r107564: Don't access freed memory in emacsclient
Date: Sun, 11 Mar 2012 12:15:25 +0100
User-agent: Bazaar (2.3.1)

------------------------------------------------------------
revno: 107564
committer: Andreas Schwab <address@hidden>
branch nick: emacs
timestamp: Sun 2012-03-11 12:15:25 +0100
message:
  Don't access freed memory in emacsclient
  
  * emacsclient.c (socket_name): Add const.
  (get_server_config): Add parameter config_file, use it instead of
  global server_file.
  (set_tcp_socket): Add parameter local_server_file, pass it down to
  get_server_config.
  (set_local_socket): Add parameter local_socket_name, use it
  instead of global socket_name.
  (set_socket): Adjust calls to set_local_socket and set_tcp_socket.
  Don't clobber global server_file or socket_name.
  (main): No longer reset server_file or socket_name.
modified:
  lib-src/ChangeLog
  lib-src/emacsclient.c
=== modified file 'lib-src/ChangeLog'
--- a/lib-src/ChangeLog 2012-02-09 07:48:22 +0000
+++ b/lib-src/ChangeLog 2012-03-11 11:15:25 +0000
@@ -1,3 +1,16 @@
+2012-03-11  Andreas Schwab  <address@hidden>
+
+       * emacsclient.c (socket_name): Add const.
+       (get_server_config): Add parameter config_file, use it instead of
+       global server_file.
+       (set_tcp_socket): Add parameter local_server_file, pass it down to
+       get_server_config.
+       (set_local_socket): Add parameter local_socket_name, use it
+       instead of global socket_name.
+       (set_socket): Adjust calls to set_local_socket and set_tcp_socket.
+       Don't clobber global server_file or socket_name.
+       (main): No longer reset server_file or socket_name.
+
 2012-01-05  Glenn Morris  <address@hidden>
 
        * ebrowse.c (version) <emacs_copyright>:

=== modified file 'lib-src/emacsclient.c'
--- a/lib-src/emacsclient.c     2012-01-19 07:21:25 +0000
+++ b/lib-src/emacsclient.c     2012-03-11 11:15:25 +0000
@@ -152,7 +152,7 @@
 const char *alternate_editor = NULL;
 
 /* If non-NULL, the filename of the UNIX socket.  */
-char *socket_name = NULL;
+const char *socket_name = NULL;
 
 /* If non-NULL, the filename of the authentication file.  */
 const char *server_file = NULL;
@@ -955,36 +955,37 @@
  * the Emacs server: host, port, and authentication string.
  */
 static int
-get_server_config (struct sockaddr_in *server, char *authentication)
+get_server_config (const char *config_file, struct sockaddr_in *server,
+                  char *authentication)
 {
   char dotted[32];
   char *port;
   FILE *config = NULL;
 
-  if (file_name_absolute_p (server_file))
-    config = fopen (server_file, "rb");
+  if (file_name_absolute_p (config_file))
+    config = fopen (config_file, "rb");
   else
     {
       const char *home = egetenv ("HOME");
 
       if (home)
         {
-         char *path = xmalloc (strlen (home) + strlen (server_file)
+         char *path = xmalloc (strlen (home) + strlen (config_file)
                                + EXTRA_SPACE);
          strcpy (path, home);
          strcat (path, "/.emacs.d/server/");
-         strcat (path, server_file);
+         strcat (path, config_file);
           config = fopen (path, "rb");
          free (path);
         }
 #ifdef WINDOWSNT
       if (!config && (home = egetenv ("APPDATA")))
         {
-         char *path = xmalloc (strlen (home) + strlen (server_file)
+         char *path = xmalloc (strlen (home) + strlen (config_file)
                                + EXTRA_SPACE);
          strcpy (path, home);
          strcat (path, "/.emacs.d/server/");
-         strcat (path, server_file);
+         strcat (path, config_file);
           config = fopen (path, "rb");
          free (path);
         }
@@ -1019,14 +1020,14 @@
 }
 
 static HSOCKET
-set_tcp_socket (void)
+set_tcp_socket (const char *local_server_file)
 {
   HSOCKET s;
   struct sockaddr_in server;
   struct linger l_arg = {1, 1};
   char auth_string[AUTH_KEY_LENGTH + 1];
 
-  if (! get_server_config (&server, auth_string))
+  if (! get_server_config (local_server_file, &server, auth_string))
     return INVALID_SOCKET;
 
   if (server.sin_addr.s_addr != inet_addr ("127.0.0.1") && !quiet)
@@ -1236,7 +1237,7 @@
 
 
 static HSOCKET
-set_local_socket (void)
+set_local_socket (const char *local_socket_name)
 {
   HSOCKET s;
   struct sockaddr_un server;
@@ -1254,27 +1255,20 @@
   server.sun_family = AF_UNIX;
 
   {
-    int sock_status = 0;
-    int default_sock = !socket_name;
-    int saved_errno = 0;
-    const char *server_name = "server";
+    int sock_status;
+    int use_tmpdir = 0;
+    int saved_errno;
+    const char *server_name = local_socket_name;
     const char *tmpdir IF_LINT ( = NULL);
     char *tmpdir_storage = NULL;
     char *socket_name_storage = NULL;
 
-    if (socket_name && !strchr (socket_name, '/')
-       && !strchr (socket_name, '\\'))
+    if (!strchr (local_socket_name, '/') && !strchr (local_socket_name, '\\'))
       {
        /* socket_name is a file name component.  */
-       server_name = socket_name;
-       socket_name = NULL;
-       default_sock = 1;       /* Try both UIDs.  */
-      }
-
-    if (default_sock)
-      {
        long uid = geteuid ();
        ptrdiff_t tmpdirlen;
+       use_tmpdir = 1;
        tmpdir = egetenv ("TMPDIR");
        if (!tmpdir)
           {
@@ -1293,26 +1287,27 @@
               tmpdir = "/tmp";
           }
        tmpdirlen = strlen (tmpdir);
-       socket_name = socket_name_storage =
+       socket_name_storage =
          xmalloc (tmpdirlen + strlen (server_name) + EXTRA_SPACE);
-       strcpy (socket_name, tmpdir);
-       sprintf (socket_name + tmpdirlen, "/emacs%ld/", uid);
-       strcat (socket_name + tmpdirlen, server_name);
+       strcpy (socket_name_storage, tmpdir);
+       sprintf (socket_name_storage + tmpdirlen, "/emacs%ld/", uid);
+       strcat (socket_name_storage + tmpdirlen, server_name);
+       local_socket_name = socket_name_storage;
       }
 
-    if (strlen (socket_name) < sizeof (server.sun_path))
-      strcpy (server.sun_path, socket_name);
+    if (strlen (local_socket_name) < sizeof (server.sun_path))
+      strcpy (server.sun_path, local_socket_name);
     else
       {
         message (TRUE, "%s: socket-name %s too long\n",
-                 progname, socket_name);
+                 progname, local_socket_name);
         fail ();
       }
 
     /* See if the socket exists, and if it's owned by us. */
     sock_status = socket_status (server.sun_path);
     saved_errno = errno;
-    if (sock_status && default_sock)
+    if (sock_status && use_tmpdir)
       {
        /* Failing that, see if LOGNAME or USER exist and differ from
           our euid.  If so, look for a socket based on the UID
@@ -1333,21 +1328,21 @@
                /* We're running under su, apparently. */
                long uid = pw->pw_uid;
                ptrdiff_t tmpdirlen = strlen (tmpdir);
-               socket_name = xmalloc (tmpdirlen + strlen (server_name)
-                                      + EXTRA_SPACE);
-               strcpy (socket_name, tmpdir);
-               sprintf (socket_name + tmpdirlen, "/emacs%ld/", uid);
-               strcat (socket_name + tmpdirlen, server_name);
+               char *user_socket_name
+                 = xmalloc (tmpdirlen + strlen (server_name) + EXTRA_SPACE);
+               strcpy (user_socket_name, tmpdir);
+               sprintf (user_socket_name + tmpdirlen, "/emacs%ld/", uid);
+               strcat (user_socket_name + tmpdirlen, server_name);
 
-               if (strlen (socket_name) < sizeof (server.sun_path))
-                 strcpy (server.sun_path, socket_name);
+               if (strlen (user_socket_name) < sizeof (server.sun_path))
+                 strcpy (server.sun_path, user_socket_name);
                else
                  {
                    message (TRUE, "%s: socket-name %s too long\n",
-                            progname, socket_name);
+                            progname, user_socket_name);
                    exit (EXIT_FAILURE);
                  }
-               free (socket_name);
+               free (user_socket_name);
 
                sock_status = socket_status (server.sun_path);
                 saved_errno = errno;
@@ -1401,6 +1396,7 @@
 set_socket (int no_exit_if_error)
 {
   HSOCKET s;
+  const char *local_server_file = server_file;
 
   INITIALIZE ();
 
@@ -1408,7 +1404,7 @@
   /* Explicit --socket-name argument.  */
   if (socket_name)
     {
-      s = set_local_socket ();
+      s = set_local_socket (socket_name);
       if ((s != INVALID_SOCKET) || no_exit_if_error)
        return s;
       message (TRUE, "%s: error accessing socket \"%s\"\n",
@@ -1418,30 +1414,29 @@
 #endif
 
   /* Explicit --server-file arg or EMACS_SERVER_FILE variable.  */
-  if (!server_file)
-    server_file = egetenv ("EMACS_SERVER_FILE");
+  if (!local_server_file)
+    local_server_file = egetenv ("EMACS_SERVER_FILE");
 
-  if (server_file)
+  if (local_server_file)
     {
-      s = set_tcp_socket ();
+      s = set_tcp_socket (local_server_file);
       if ((s != INVALID_SOCKET) || no_exit_if_error)
        return s;
 
       message (TRUE, "%s: error accessing server file \"%s\"\n",
-              progname, server_file);
+              progname, local_server_file);
       exit (EXIT_FAILURE);
     }
 
 #ifndef NO_SOCKETS_IN_FILE_SYSTEM
   /* Implicit local socket.  */
-  s = set_local_socket ();
+  s = set_local_socket ("server");
   if (s != INVALID_SOCKET)
     return s;
 #endif
 
   /* Implicit server file.  */
-  server_file = "server";
-  s = set_tcp_socket ();
+  s = set_tcp_socket ("server");
   if ((s != INVALID_SOCKET) || no_exit_if_error)
     return s;
 
@@ -1573,8 +1568,6 @@
   int rl = 0, needlf = 0;
   char *cwd, *str;
   char string[BUFSIZ+1];
-  int null_socket_name IF_LINT ( = 0);
-  int null_server_file IF_LINT ( = 0);
   int start_daemon_if_needed;
   int exit_status = EXIT_SUCCESS;
 
@@ -1602,14 +1595,6 @@
      in case of failure to connect.  */
   start_daemon_if_needed = (alternate_editor
                            && (alternate_editor[0] == '\0'));
-  if (start_daemon_if_needed)
-    {
-      /* set_socket changes the values for socket_name and
-        server_file, we need to reset them, if they were NULL before
-        for the second call to set_socket.  */
-      null_socket_name = (socket_name == NULL);
-      null_server_file = (server_file == NULL);
-    }
 
   emacs_socket = set_socket (alternate_editor || start_daemon_if_needed);
   if (emacs_socket == INVALID_SOCKET)
@@ -1617,13 +1602,6 @@
       if (! start_daemon_if_needed)
        fail ();
 
-      /* Reset socket_name and server_file if they were NULL
-        before the set_socket call.  */
-      if (null_socket_name)
-       socket_name = NULL;
-      if (null_server_file)
-       server_file = NULL;
-
       start_daemon_and_retry_set_socket ();
     }
 


reply via email to

[Prev in Thread] Current Thread [Next in Thread]