Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.89) (envelope-from ) id 1iz4O9-0004UM-UC for pgsql-hackers@arkaria.postgresql.org; Tue, 04 Feb 2020 20:01:38 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.89) (envelope-from ) id 1iz4O8-00032C-F4 for pgsql-hackers@arkaria.postgresql.org; Tue, 04 Feb 2020 20:01:36 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.89) (envelope-from <9erthalion6@gmail.com>) id 1iz4O8-000324-3X for pgsql-hackers@lists.postgresql.org; Tue, 04 Feb 2020 20:01:36 +0000 Received: from mail-ed1-x544.google.com ([2a00:1450:4864:20::544]) by magus.postgresql.org with esmtps (TLS1.3:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.92) (envelope-from <9erthalion6@gmail.com>) id 1iz4O5-0007Ow-P0 for pgsql-hackers@postgresql.org; Tue, 04 Feb 2020 20:01:35 +0000 Received: by mail-ed1-x544.google.com with SMTP id c26so21053346eds.8 for ; Tue, 04 Feb 2020 12:01:33 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=date:from:to:cc:subject:message-id:references:mime-version :content-disposition:in-reply-to; bh=710KPdvpjW05mLuQtD/6goMGtD50241kU7/yG6f5Gqw=; b=cACaiFcfIdYVd4UOmtloMW+vrWVJhSwUgLqQJWSdcXpoKRv9n3U+s+SqKJGmGZev4A y3VIk5birViDHmBeKFVqIoVxBE6zLloFLHF2KR4G+wYKLVTPBYETfVtqBfe5Goc2MC8T 44SmeoUC3EDctj6TR8X/MtFTRbG9eRHlE0r+PwoMY1Xhp9Ck1IT8pwzV9ATYf3p1FAbC WYuSG1U8X6P+bw01nN0lXSZiUzA0XbwjQOZH+Rs+JY7ODxqa1VcSHOelwBd6eKmIFwhd J+BeamwMOvgUovRwQ4Nvq0a4J+4XQq62uYifRc5BFlRzmgARtum4OwEnd1HIUk7iLxOT CXXA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:date:from:to:cc:subject:message-id:references :mime-version:content-disposition:in-reply-to; bh=710KPdvpjW05mLuQtD/6goMGtD50241kU7/yG6f5Gqw=; b=PIXUNg3SFDisRLquCUODB3VzOGhL+tYjCo3sYnoffDEv2YR4g/SnRC7TBAYpqnYDEB ueDxvhOfxBh6UHqKH94OWsvRtqhP+E3KIO3T1mWhuDuF+XFMnqQP8FKUEZjMhZ0+Wjnk l9kO3UlWatAIKnZX4aOqI4RfLjhdGswNXHizpyeApKTt0luELj+P7b8ldSnCUF1FZ2hS PU9zEKKkFohdfG4JkvVA2k34y70hb3++fJNgSL1CyABiJpD3nZVwoDI8ec9iqMEp/9dl v66LUtNq6VqISuWHrxJ57LqsJkdnTqcZpvGgpe5Zivqt0BPFcs3RNFOdFNkmU4RXSIGV VbMQ== X-Gm-Message-State: APjAAAUeqzI0Eq91GdQeWy+XjSnb6sbLfU6YenXqxeb+pO7ViDVS9K4u qcqeY0IbFfhgPloV156NNww= X-Google-Smtp-Source: APXvYqw05QB0zrpEvMpOp9b1HDEi85to6AA3tsmwaWIxQiwiiW2TXZS8nY5dIIwbhR9EyMu5ez/h4g== X-Received: by 2002:a50:e046:: with SMTP id g6mr1958861edl.172.1580846492065; Tue, 04 Feb 2020 12:01:32 -0800 (PST) Received: from localhost (dslb-094-222-004-201.094.222.pools.vodafone-ip.de. [94.222.4.201]) by smtp.gmail.com with ESMTPSA id qk16sm1458475ejb.71.2020.02.04.12.01.29 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Tue, 04 Feb 2020 12:01:30 -0800 (PST) Date: Tue, 4 Feb 2020 21:02:05 +0100 From: Dmitry Dolgov <9erthalion6@gmail.com> To: Floris Van Nee Cc: Peter Geoghegan , Jesper Pedersen , David Rowley , Tomas Vondra , Kyotaro Horiguchi , Alvaro Herrera , Thomas Munro , James Coleman , Rafia Sabih , Jeff Janes , Bhushan Uparkar , PostgreSQL-development , Alexander Korotkov Subject: Re: Index Skip Scan Message-ID: <20200204200205.ip5c2mzy3i2okqey@localhost> References: <1e59d800b38141c5af2ad3a64cf9758e@opammb0562.comp.optiver.com> <802e46fa-dc2c-4c32-e55b-884e04aa7f12@redhat.com> <20200121160942.eu4bvbu46nt223ug@localhost> <20200122160441.ograupmzyytde2mi@localhost> <1579713885361.64964@Optiver.com> <20200122213603.ndlm6t4ryivdwxs7@localhost> <20200127103016.ieflsboqveb6iduc@localhost> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Precedence: bulk > On Mon, Jan 27, 2020 at 02:00:39PM +0000, Floris Van Nee wrote: > > Thanks for the new patch! I tested it and managed to find a case that causes > some issues. Here's how to reproduce: So, after a bit of investigation I found out the issue (it was actually there even in the previous version). In this only case of moving forward and reading backward, exactly scenarious you've described above, current implementation was not ignoring deleted tuples. My first idea to fix this was to use _bt_readpage when necessary and put couple of _bt_killitems when we leave a page while jumping before, so that deleted tuples will be ignored. To demonstrate it visually, let's say we want to go backward on a cursor over an ORDER BY a DESC, b DESC query, i.e. return: (1,100), (2, 100), (3, 100) etc. To achieve that we jump from (1,1) to (1,100), from (2,1) to (2,100) and so on. If some values are deleted, we need to read backward. E.g. if (3,100) is deleted, we need to return (3,99). +---------------+---------------+---------------+---------------+ | | | | | | 1,1 ... 1,100 | 2,1 ... 2,100 | 3,1 ... 3,100 | 4,1 ... 4,100 | | | | | | +---------------+---------------+---------------+---------------+ | ^ | ^ | ^ | ^ | | | | | | | | +-------------+ +-------------+ +-------------+ +-------------+ If it happened that a whole value series is deleted, we return to the previous value and need to detect such situation. E.g. if all the values from (3,1) to (3,100) were deleted, we will return to (2,100). +---------------+---------------+ +---------------+ | | | | | | 1,1 ... 1,100 | 2,1 ... 2,100 |<--------------+ 4,1 ... 4,100 | | | | | | +---------------+---------------+ +---------------+ ^ | ^ | ^ | ^ | | | | | | | | +-------------+ +-------------+ +-------------+ | +-----------------------------+ This all is implemented inside _bt_skip. Unfortunately as I see it now the idea of relying on ability to skip dead index tuples without checking a heap tuple is not reliable, since an index tuple will be added into killedItems and can be marked as dead only when not a single transaction can see it anymore. Potentially there are two possible solutions: * Adjust the code in nodeIndexOnlyscan to perform a proper visibility check and understand if we returned back. Obviously it will make the patch more invasive. * Reduce scope of the patch, and simply do not apply jumping in this case. This means less functionality but hopefully still brings some value. At this point me and Jesper inclined to go with the second option. But maybe I'm missing something, are there any other suggestions?