v13-0005-Fix-incorrect-filtering-condition-in-iteration.patch
application/octet-stream
Filename: v13-0005-Fix-incorrect-filtering-condition-in-iteration.patch
Type: application/octet-stream
Part: 4
Patch
Same data as JSON:
GET /api/v1/attachments/:id/patch
the parsed metadata as JSON — format, series position, per-file stats; never the diff bytes.
API reference →
Format: format-patch
Series: patch v13-0005
Subject: Fix incorrect filtering condition in iteration
| File | + | − |
|---|---|---|
| src/backend/optimizer/path/equivclass.c | 30 | 38 |
From 401c2ddf9ce72cccbe39e908737d68a6704c7926 Mon Sep 17 00:00:00 2001
From: Yuya Watari <watari.yuya@gmail.com>
Date: Mon, 30 Jan 2023 09:46:56 +0900
Subject: [PATCH v13 5/7] Fix incorrect filtering condition in iteration
The original code incorrectly missed EquivalenceMembers with empty
em_relids when 'with_norel_members' is true in
eclass_member_iterator_strict_next(). Such an EM passes the second if
condition, but fails the last condition because it cannot be superset of
non-empty relids.
---
src/backend/optimizer/path/equivclass.c | 68 +++++++++++--------------
1 file changed, 30 insertions(+), 38 deletions(-)
diff --git a/src/backend/optimizer/path/equivclass.c b/src/backend/optimizer/path/equivclass.c
index 561f50cafa..83ea0313e1 100644
--- a/src/backend/optimizer/path/equivclass.c
+++ b/src/backend/optimizer/path/equivclass.c
@@ -3733,26 +3733,22 @@ eclass_member_iterator_next(EquivalenceMemberIterator *iter)
{
EquivalenceMember *em = lfirst_node(EquivalenceMember, lc);
- if (!iter->with_children && em->em_is_child)
- continue;
-
- if (!iter->with_norel_members && bms_is_empty(em->em_relids))
- continue;
-
- if (!bms_overlap(em->em_relids, iter->with_relids))
- continue;
-
- iter->current_index = foreach_current_index(lc);
+ if ((iter->with_norel_members && bms_is_empty(em->em_relids))
+ || (bms_overlap(em->em_relids, iter->with_relids)
+ && (iter->with_children || !em->em_is_child)))
+ {
+ iter->current_index = foreach_current_index(lc);
- /*
- * Some users of this iterator will be adding new
- * EquivalenceMember during the loop. We must ensure we don't
- * return those, so here we return NULL when the loop index goes
- * beyond the original length of the ec_members list.
- */
- if (iter->current_index >= iter->orig_length)
- return NULL;
- return em;
+ /*
+ * Some users of this iterator will be adding new
+ * EquivalenceMember during the loop. We must ensure we don't
+ * return those, so here we return NULL when the loop index goes
+ * beyond the original length of the ec_members list.
+ */
+ if (iter->current_index >= iter->orig_length)
+ return NULL;
+ return em;
+ }
}
return NULL;
}
@@ -3784,26 +3780,22 @@ eclass_member_iterator_strict_next(EquivalenceMemberIterator *iter)
{
EquivalenceMember *em = lfirst_node(EquivalenceMember, lc);
- if (!iter->with_children && em->em_is_child)
- continue;
-
- if (!iter->with_norel_members && bms_is_empty(em->em_relids))
- continue;
-
- if (!bms_is_subset(iter->with_relids, em->em_relids))
- continue;
-
- iter->current_index = foreach_current_index(lc);
+ if ((iter->with_norel_members && bms_is_empty(em->em_relids))
+ || (bms_is_subset(iter->with_relids, em->em_relids)
+ && (iter->with_children || !em->em_is_child)))
+ {
+ iter->current_index = foreach_current_index(lc);
- /*
- * Some users of this iterator will be adding new
- * EquivalenceMember during the loop. We must ensure we don't
- * return those, so here we return NULL when the loop index goes
- * beyond the original length of the ec_members list.
- */
- if (iter->current_index >= iter->orig_length)
- return NULL;
- return em;
+ /*
+ * Some users of this iterator will be adding new
+ * EquivalenceMember during the loop. We must ensure we don't
+ * return those, so here we return NULL when the loop index goes
+ * beyond the original length of the ec_members list.
+ */
+ if (iter->current_index >= iter->orig_length)
+ return NULL;
+ return em;
+ }
}
return NULL;
}
--
2.35.3.windows.1