mono_attach_load_agent: Fix leaks, alloc, copy. (mono/mono#15950)
authorJay Krell <jaykrell@microsoft.com>
Tue, 27 Aug 2019 07:46:35 +0000 (00:46 -0700)
committerAlexander Köplinger <alex.koeplinger@outlook.com>
Tue, 27 Aug 2019 07:46:35 +0000 (09:46 +0200)
Extracted and slightly modified from https://github.com/mono/mono/pull/15868.

Commit migrated from https://github.com/mono/mono/commit/7ca15e5a42ad03572e9209abb7e030ad712ee4b5

src/mono/configure.ac
src/mono/mono/metadata/attach.c

index 7207324..18fd31a 100644 (file)
@@ -62,7 +62,7 @@ MONO_VERSION_BUILD=`echo $VERSION | cut -d . -f 3`
 # This line is parsed by tools besides autoconf, such as msvc/mono.winconfig.targets.
 # It should remain in the format they expect.
 #
-MONO_CORLIB_VERSION=69f9feb5-e6ef-4d90-8722-17346c85efb6
+MONO_CORLIB_VERSION=90c44d62-c1dd-4a52-bf0e-ac282fcc8be8
 
 #
 # Put a quoted #define in config.h.
index d8453cc..72d994d 100644 (file)
@@ -110,30 +110,26 @@ static void transport_start_receive (void);
 /*
  * Functions to decode protocol data
  */
-static inline int
-decode_byte (guint8 *buf, guint8 **endbuf, guint8 *limit)
+static int
+decode_byte (guint8 const *buf, guint8 const **endbuf, guint8 const *limit)
 {
        *endbuf = buf + 1;
        g_assert (*endbuf <= limit);
        return buf [0];
 }
 
-static inline int
-decode_int (guint8 *buf, guint8 **endbuf, guint8 *limit)
+static int
+decode_int (const guint8 *buf)
 {
-       *endbuf = buf + 4;
-       g_assert (*endbuf <= limit);
-
        return (((int)buf [0]) << 0) | (((int)buf [1]) << 8) | (((int)buf [2]) << 16) | (((int)buf [3]) << 24);
 }
 
-static char*
-decode_string_value (guint8 *buf, guint8 **endbuf, guint8 *limit)
+static const char*
+decode_string_value (guint8 const *buf, guint8 const **endbuf, guint8 const *limit)
 {
        int type;
-    gint32 length;
-       guint8 *p = buf;
-       char *s;
+       gint32 length;
+       guint8 const *p = buf;
 
        type = decode_byte (p, &p, limit);
        if (type == PRIM_TYPE_NULL) {
@@ -154,12 +150,10 @@ decode_string_value (guint8 *buf, guint8 **endbuf, guint8 *limit)
 
        g_assert (length < (1 << 16));
 
-       s = (char *)g_malloc (length + 1);
+       const char *s = (const char*)p;
+       p += length + 1;
 
-       g_assert (p + length <= limit);
-       memcpy (s, p, length);
-       s [length] = '\0';
-       p += length;
+       g_assert (p <= limit);
 
        *endbuf = p;
 
@@ -502,9 +496,6 @@ transport_start_receive (void)
 static gsize WINAPI
 receiver_thread (void *arg)
 {
-       int res, content_len;
-       guint8 buffer [256];
-       guint8 *p, *p_end;
        MonoInternalThread *internal = mono_thread_internal_current ();
 
        mono_thread_set_name_constant_ignore_error (internal, "Attach receiver", MonoSetThreadNameFlag_Permanent);
@@ -527,10 +518,10 @@ receiver_thread (void *arg)
                guint8* body = NULL;
 
                while (TRUE) {
-                       char *cmd, *agent_name, *agent_args;
+                       guint8 buffer [6];
 
                        /* Read Header */
-                       res = read (conn_fd, buffer, 6);
+                       int res = read (conn_fd, buffer, 6);
 
                        if (res == -1 && errno == EINTR)
                                continue;
@@ -541,7 +532,7 @@ receiver_thread (void *arg)
                        if (res != 6)
                                break;
 
-                       if ((strncmp ((char*)buffer, "MONO", 4) != 0) || buffer [4] != 1 || buffer [5] != 0) {
+                       if (memcmp (buffer, "MONO", 4) != 0 || buffer [4] != 1 || buffer [5] != 0) {
                                fprintf (stderr, "attach: message from server has unknown header.\n");
                                break;
                        }
@@ -551,32 +542,30 @@ receiver_thread (void *arg)
                        if (res != 4)
                                break;
 
-                       p = buffer;
-                       p_end = p + 8;
-
-                       content_len = decode_int (p, &p, p_end);
+                       const int content_len = decode_int (buffer);
 
                        /* Read message body */
                        body = (guint8 *)g_malloc (content_len);
                        res = read (conn_fd, body, content_len);
-                       
-                       p = body;
-                       p_end = body + content_len;
+                       if (res != content_len)
+                               break;
+
+                       guint8 const * p = body;
+                       guint8 const * const p_end = body + content_len;
 
-                       cmd = decode_string_value (p, &p, p_end);
+                       char const * const cmd = decode_string_value (p, &p, p_end);
                        if (cmd == NULL)
                                break;
-                       g_assert (!strcmp (cmd, "attach"));
 
-                       agent_name = decode_string_value (p, &p, p_end);
-                       agent_args = decode_string_value (p, &p, p_end);
+                       // 10: 7:attach\0 + one byte each for the types of cmd, name, args.
+                       g_assert (content_len >= 10 && !memcmp (cmd, "attach", 7));
+
+                       char const * const agent_name = decode_string_value (p, &p, p_end);
+                       char const * const agent_args = decode_string_value (p, &p, p_end);
 
                        printf ("attach: Loading agent '%s'.\n", agent_name);
                        mono_attach_load_agent (mono_domain_get (), agent_name, agent_args);
 
-                       g_free (agent_name);
-                       g_free (agent_args);
-
                        g_free (body);
                        body = NULL;