Code

frontend: Make sure to not read to much from a connection buffer.
authorSebastian Harl <sh@tokkee.org>
Sat, 2 Aug 2014 15:10:49 +0000 (17:10 +0200)
committerSebastian Harl <sh@tokkee.org>
Sat, 2 Aug 2014 15:10:49 +0000 (17:10 +0200)
The current command, as stored in the connection buffer, is not necessarily
nil-terminated. That's only the case if there's no further data in the buffer
(which will *often* be the case in the current implementation when using
'sysdb' as the client) but the code should never rely on that.

In cases where the function operating on the data does not support specifying
the length of the string to work on, copy the data to a temporary buffer
first.

src/frontend/connection.c

index 777775053af71f0c6ec2fb88d788d47d9f06592d..0bdafdc89b0dce2687d064db21e42f791c9f997e 100644 (file)
@@ -281,8 +281,11 @@ command_handle(sdb_conn_t *conn)
                        parsetree = sdb_fe_parse(sdb_strbuf_string(conn->buf),
                                        (int)conn->cmd_len);
                        if (! parsetree) {
+                               char query[conn->cmd_len + 1];
+                               strncpy(query, sdb_strbuf_string(conn->buf), conn->cmd_len);
+                               query[sizeof(query) - 1] = '\0';
                                sdb_log(SDB_LOG_ERR, "frontend: Failed to parse query '%s'",
-                                               sdb_strbuf_string(conn->buf));
+                                               query);
                                status = -1;
                                break;
                        }
@@ -296,12 +299,17 @@ command_handle(sdb_conn_t *conn)
                                        break;
 
                                default:
+                               {
+                                       char query[conn->cmd_len + 1];
+                                       strncpy(query, sdb_strbuf_string(conn->buf), conn->cmd_len);
+                                       query[sizeof(query) - 1] = '\0';
                                        sdb_log(SDB_LOG_WARNING, "frontend: Ignoring %d command%s "
                                                        "in multi-statement query '%s'",
                                                        sdb_llist_len(parsetree) - 1,
                                                        sdb_llist_len(parsetree) == 2 ? "" : "s",
-                                                       sdb_strbuf_string(conn->buf));
+                                                       query);
                                        node = SDB_CONN_NODE(sdb_llist_get(parsetree, 0));
+                               }
                        }
 
                        if (node) {
@@ -314,9 +322,13 @@ command_handle(sdb_conn_t *conn)
                }
 
                case CONNECTION_FETCH:
-                       status = sdb_fe_fetch(conn, sdb_strbuf_string(conn->buf),
-                                       /* filter = */ NULL);
+               {
+                       char hostname[conn->cmd_len + 1];
+                       strncpy(hostname, sdb_strbuf_string(conn->buf), conn->cmd_len);
+                       hostname[sizeof(hostname) - 1] = '\0';
+                       status = sdb_fe_fetch(conn, hostname, /* filter = */ NULL);
                        break;
+               }
                case CONNECTION_LIST:
                        status = sdb_fe_list(conn, /* filter = */ NULL);
                        break;
@@ -327,8 +339,11 @@ command_handle(sdb_conn_t *conn)
                        m = sdb_fe_parse_matcher(sdb_strbuf_string(conn->buf),
                                        (int)conn->cmd_len);
                        if (! m) {
-                               sdb_log(SDB_LOG_ERR, "frontend: Failed to parse expression '%s'",
-                                               sdb_strbuf_string(conn->buf));
+                               char expr[conn->cmd_len + 1];
+                               strncpy(expr, sdb_strbuf_string(conn->buf), conn->cmd_len);
+                               expr[sizeof(expr) - 1] = '\0';
+                               sdb_log(SDB_LOG_ERR, "frontend: Failed to parse "
+                                               "lookup condition '%s'", expr);
                                status = -1;
                                break;
                        }