Tarantool development patches archive
 help / color / mirror / Atom feed
From: Vladimir Davydov <vdavydov.dev@gmail.com>
To: tarantool-patches@freelists.org
Subject: [PATCH] xrow: fix request_str crash on long requests
Date: Mon, 18 Mar 2019 19:45:29 +0300	[thread overview]
Message-ID: <234177c19ce6bdc86ba64555f02f8fb76e3768a0.1552927469.git.vdavydov.dev@gmail.com> (raw)

If tt_static_buf is too small to store the request string, 'pos' will
become greater than 'end', leading to snprintf(pos, end - pos) crash, as
it doesn't allow the buffer size to be negative. Use SNPRINT instead.
---
https://github.com/tarantool/tarantool/tree/dv/fix-request-str-crash-on-long-requests

 src/box/xrow.c            | 33 ++++++++++++++++++++-------------
 test/box-tap/cfg.test.lua | 21 ++++++++++++++++++++-
 2 files changed, 40 insertions(+), 14 deletions(-)

diff --git a/src/box/xrow.c b/src/box/xrow.c
index bddae1d5..4a0632fe 100644
--- a/src/box/xrow.c
+++ b/src/box/xrow.c
@@ -675,13 +675,11 @@ done:
 	return 0;
 }
 
-const char *
-request_str(const struct request *request)
+static int
+request_snprint(char *buf, int size, const struct request *request)
 {
-	char *buf = tt_static_buf();
-	char *end = buf + TT_STATIC_BUF_LEN;
-	char *pos = buf;
-	pos += snprintf(pos, end - pos, "{type: '%s', "
+	int total = 0;
+	SNPRINT(total, snprintf, buf, size, "{type: '%s', "
 			"replica_id: %u, lsn: %lld, "
 			"space_id: %u, index_id: %u",
 			iproto_type_name(request->type),
@@ -690,18 +688,27 @@ request_str(const struct request *request)
 			(unsigned) request->space_id,
 			(unsigned) request->index_id);
 	if (request->key != NULL) {
-		pos += snprintf(pos, end - pos, ", key: ");
-		pos += mp_snprint(pos, end - pos, request->key);
+		SNPRINT(total, snprintf, buf, size, ", key:");
+		SNPRINT(total, mp_snprint, buf, size, request->key);
 	}
 	if (request->tuple != NULL) {
-		pos += snprintf(pos, end - pos, ", tuple: ");
-		pos += mp_snprint(pos, end - pos, request->tuple);
+		SNPRINT(total, snprintf, buf, size, ", tuple");
+		SNPRINT(total, mp_snprint, buf, size, request->tuple);
 	}
 	if (request->ops != NULL) {
-		pos += snprintf(pos, end - pos, ", ops: ");
-		pos += mp_snprint(pos, end - pos, request->ops);
+		SNPRINT(total, snprintf, buf, size, ", ops: ");
+		SNPRINT(total, mp_snprint, buf, size, request->ops);
 	}
-	pos += snprintf(pos, end - pos, "}");
+	SNPRINT(total, snprintf, buf, size, "}");
+	return total;
+}
+
+const char *
+request_str(const struct request *request)
+{
+	char *buf = tt_static_buf();
+	if (request_snprint(buf, TT_STATIC_BUF_LEN, request) < 0)
+		return "<failed to format request>";
 	return buf;
 }
 
diff --git a/test/box-tap/cfg.test.lua b/test/box-tap/cfg.test.lua
index f791cc3f..55de5e41 100755
--- a/test/box-tap/cfg.test.lua
+++ b/test/box-tap/cfg.test.lua
@@ -6,7 +6,7 @@ local socket = require('socket')
 local fio = require('fio')
 local uuid = require('uuid')
 local msgpack = require('msgpack')
-test:plan(102)
+test:plan(104)
 
 --------------------------------------------------------------------------------
 -- Invalid values
@@ -566,5 +566,24 @@ os.exit(0)
 ]]
 test:is(run_script(code), 0, "log_nonblock")
 
+--
+-- Crash (instead of panic) when trying to recover a huge tuple.
+--
+dir = fio.tempdir()
+code1 = string.format([[
+box.cfg{wal_dir = '%s', memtx_dir = '%s', memtx_max_tuple_size = 10 * 1024 * 1024}
+box.schema.space.create('test')
+box.space.test:create_index('primary')
+box.space.test:insert{1, string.rep('x', 1024 * 1024)}
+os.exit(0)
+]], dir, dir)
+code2 = string.format([[
+box.cfg{wal_dir = '%s', memtx_dir = '%s', memtx_max_tuple_size = 10 * 1024}
+os.exit(0)
+]], dir, dir)
+test:is(run_script(code1), 0, "create huge tuple")
+test:is(run_script(code2), PANIC, "panic on huge tuple recovery")
+fio.rmtree(dir)
+
 test:check()
 os.exit(0)
-- 
2.11.0

             reply	other threads:[~2019-03-18 16:45 UTC|newest]

Thread overview: 3+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2019-03-18 16:45 Vladimir Davydov [this message]
2019-03-18 17:01 ` Vladimir Davydov
2019-03-18 17:53   ` Vladimir Davydov

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=234177c19ce6bdc86ba64555f02f8fb76e3768a0.1552927469.git.vdavydov.dev@gmail.com \
    --to=vdavydov.dev@gmail.com \
    --cc=tarantool-patches@freelists.org \
    --subject='Re: [PATCH] xrow: fix request_str crash on long requests' \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox