From 62c1241b7a9afc711df4f1da2dc042b6e4d487e9 Mon Sep 17 00:00:00 2001 From: Yiding Cui Date: Tue, 23 Oct 2018 14:24:28 +0800 Subject: [PATCH] executor: fix panic when limit is too large (#7936) (#8004) --- executor/executor_test.go | 4 ++++ executor/sort.go | 8 ++++---- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/executor/executor_test.go b/executor/executor_test.go index c8c5ccd228188..dd038af049f7d 100644 --- a/executor/executor_test.go +++ b/executor/executor_test.go @@ -641,6 +641,10 @@ func (s *testSuite) TestSelectOrderBy(c *C) { r = tk.MustQuery("select * from select_order_test order by name, id limit 1 offset 100;") r.Check(testkit.Rows()) + // Test limit exceeds int range. + r = tk.MustQuery("select id from select_order_test order by name, id limit 18446744073709551615;") + r.Check(testkit.Rows("1", "2")) + // Test multiple field r = tk.MustQuery("select id, name from select_order_test where id = 1 group by id, name limit 1 offset 0;") r.Check(testkit.Rows("1 hello")) diff --git a/executor/sort.go b/executor/sort.go index e77455dd87eed..40794a0dfc09d 100644 --- a/executor/sort.go +++ b/executor/sort.go @@ -222,7 +222,7 @@ func (e *SortExec) keyChunksLess(i, j int) bool { type TopNExec struct { SortExec limit *plan.PhysicalLimit - totalLimit int + totalLimit uint64 chkHeap *topNChunkHeap } @@ -298,7 +298,7 @@ func (e *TopNExec) Open(ctx context.Context) error { func (e *TopNExec) Next(ctx context.Context, chk *chunk.Chunk) error { chk.Reset() if !e.fetched { - e.totalLimit = int(e.limit.Offset + e.limit.Count) + e.totalLimit = e.limit.Offset + e.limit.Count e.Idx = int(e.limit.Offset) err := e.loadChunksUntilTotalLimit(ctx) if err != nil { @@ -326,7 +326,7 @@ func (e *TopNExec) loadChunksUntilTotalLimit(ctx context.Context) error { e.rowChunks = chunk.NewList(e.retTypes(), e.maxChunkSize) e.rowChunks.GetMemTracker().AttachTo(e.memTracker) e.rowChunks.GetMemTracker().SetLabel("rowChunks") - for e.rowChunks.Len() < e.totalLimit { + for uint64(e.rowChunks.Len()) < e.totalLimit { srcChk := e.children[0].newChunk() err := e.children[0].Next(ctx, srcChk) if err != nil { @@ -354,7 +354,7 @@ const topNCompactionFactor = 4 func (e *TopNExec) executeTopN(ctx context.Context) error { heap.Init(e.chkHeap) - for len(e.rowPtrs) > e.totalLimit { + for uint64(len(e.rowPtrs)) > e.totalLimit { // The number of rows we loaded may exceeds total limit, remove greatest rows by Pop. heap.Pop(e.chkHeap) }