diff options
author | Tatsuo Ishii <ishii@postgresql.org> | 2025-10-08 09:26:49 +0900 |
---|---|---|
committer | Tatsuo Ishii <ishii@postgresql.org> | 2025-10-08 09:26:49 +0900 |
commit | 2273fa32bce7c1fb856c726d01d8cdaaba36f849 (patch) | |
tree | c98c8ca83c9e9acb89ef9e952460530312cb7a54 /src | |
parent | 3bf905692c9db5309c5cd4c0dec7ec17ab8c7af1 (diff) |
Fix Coverity issues reported in commit 25a30bbd423.HEADorigin/masterorigin/HEADmaster
Fix several issues pointed out by Coverity (reported by Tome Lane).
- In row_is_in_frame(), return value of window_gettupleslot() was not
checked.
- WinGetFuncArgInPartition() tried to derefference "isout" pointer
even if it could be NULL in some places.
Besides the issues, I also fixed a compiler warning reported by Álvaro
Herrera.
Moreover, in WinGetFuncArgInPartition refactor the do...while loop so
that the codes inside the loop simpler. Also simplify the case when
abs_pos < 0.
Author: Tatsuo Ishii <ishii@postgresql.org>
Reviewed-by: Paul Ramsey <pramsey@cleverelephant.ca>
Reported-by: Tom Lane <tgl@sss.pgh.pa.us>
Reported-by: Álvaro Herrera <alvherre@kurilemu.de>
Discussion: https://postgr.es/m/1686755.1759679957%40sss.pgh.pa.us
Discussion: https://postgr.es/m/202510051612.gw67jlc2iqpw%40alvherre.pgsql
Diffstat (limited to 'src')
-rw-r--r-- | src/backend/executor/nodeWindowAgg.c | 77 |
1 files changed, 38 insertions, 39 deletions
diff --git a/src/backend/executor/nodeWindowAgg.c b/src/backend/executor/nodeWindowAgg.c index cf667c81211..0698aae37a7 100644 --- a/src/backend/executor/nodeWindowAgg.c +++ b/src/backend/executor/nodeWindowAgg.c @@ -1501,8 +1501,9 @@ row_is_in_frame(WindowObject winobj, int64 pos, TupleTableSlot *slot, /* following row that is not peer is out of frame */ if (pos > winstate->currentpos) { - if (fetch_tuple) - window_gettupleslot(winobj, pos, slot); + if (fetch_tuple) /* need to fetch tuple? */ + if (!window_gettupleslot(winobj, pos, slot)) + return -1; if (!are_peers(winstate, slot, winstate->ss.ss_ScanTupleSlot)) return -1; } @@ -3721,6 +3722,7 @@ WinGetFuncArgInPartition(WindowObject winobj, int argno, int notnull_offset; int notnull_relpos; int forward; + bool myisout; Assert(WindowObjectIsValid(winobj)); winstate = winobj->winstate; @@ -3759,63 +3761,60 @@ WinGetFuncArgInPartition(WindowObject winobj, int argno, if (!null_treatment) /* IGNORE NULLS is not specified */ { + /* get tupple and evaluate in a partition */ datum = gettuple_eval_partition(winobj, argno, - abs_pos, isnull, isout); - if (!*isout && set_mark) + abs_pos, isnull, &myisout); + if (!myisout && set_mark) WinSetMarkPosition(winobj, abs_pos); + if (isout) + *isout = myisout; return datum; } + myisout = false; + datum = 0; + /* * Get the next nonnull value in the partition, moving forward or backward * until we find a value or reach the partition's end. */ do { + int nn_info; /* NOT NULL info */ + abs_pos += forward; - if (abs_pos < 0) - { - /* out of partition */ - if (isout) - *isout = true; - *isnull = true; - datum = 0; + if (abs_pos < 0) /* apparently out of partition */ break; - } - switch (get_notnull_info(winobj, abs_pos)) + /* check NOT NULL cached info */ + nn_info = get_notnull_info(winobj, abs_pos); + if (nn_info == NN_NOTNULL) /* this row is known to be NOT NULL */ + notnull_offset++; + + else if (nn_info == NN_NULL) /* this row is known to be NULL */ + continue; /* keep on moving forward or backward */ + + else /* need to check NULL or not */ { - case NN_NOTNULL: /* this row is known to be NOT NULL */ - notnull_offset++; - if (notnull_offset >= notnull_relpos) - { - /* prepare to exit this loop */ - datum = gettuple_eval_partition(winobj, argno, - abs_pos, isnull, isout); - } - break; - case NN_NULL: /* this row is known to be NULL */ - if (isout) - *isout = false; - *isnull = true; - datum = 0; - break; - default: /* need to check NULL or not */ - datum = gettuple_eval_partition(winobj, argno, - abs_pos, isnull, isout); - if (*isout) /* out of partition? */ - return datum; - - if (!*isnull) - notnull_offset++; - /* record the row status */ - put_notnull_info(winobj, abs_pos, *isnull); + /* get tupple and evaluate in a partition */ + datum = gettuple_eval_partition(winobj, argno, + abs_pos, isnull, &myisout); + if (myisout) /* out of partition? */ break; + if (!*isnull) + notnull_offset++; + /* record the row status */ + put_notnull_info(winobj, abs_pos, *isnull); } } while (notnull_offset < notnull_relpos); - if (!*isout && set_mark) + /* get tupple and evaluate in a partition */ + datum = gettuple_eval_partition(winobj, argno, + abs_pos, isnull, &myisout); + if (!myisout && set_mark) WinSetMarkPosition(winobj, abs_pos); + if (isout) + *isout = myisout; return datum; } |