PostgreSQL Source Code git master
Loading...
Searching...
No Matches
windowapi.h File Reference
#include "fmgr.h"
Include dependency graph for windowapi.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Macros

#define WINDOW_SEEK_CURRENT   0
 
#define WINDOW_SEEK_HEAD   1
 
#define WINDOW_SEEK_TAIL   2
 
#define PG_WINDOW_OBJECT()   ((WindowObject) fcinfo->context)
 
#define WindowObjectIsValid(winobj)    ((winobj) != NULL && IsA(winobj, WindowObjectData))
 

Typedefs

typedef struct WindowObjectDataWindowObject
 

Functions

void WinCheckAndInitializeNullTreatment (WindowObject winobj, bool allowNullTreatment, FunctionCallInfo fcinfo)
 
voidWinGetPartitionLocalMemory (WindowObject winobj, Size sz)
 
int64 WinGetCurrentPosition (WindowObject winobj)
 
int64 WinGetPartitionRowCount (WindowObject winobj)
 
void WinSetMarkPosition (WindowObject winobj, int64 markpos)
 
bool WinRowsArePeers (WindowObject winobj, int64 pos1, int64 pos2)
 
Datum WinGetFuncArgInPartition (WindowObject winobj, int argno, int relpos, int seektype, bool set_mark, bool *isnull, bool *isout)
 
Datum WinGetFuncArgInFrame (WindowObject winobj, int argno, int relpos, int seektype, bool set_mark, bool *isnull, bool *isout)
 
Datum WinGetFuncArgCurrent (WindowObject winobj, int argno, bool *isnull)
 

Macro Definition Documentation

◆ PG_WINDOW_OBJECT

#define PG_WINDOW_OBJECT ( )    ((WindowObject) fcinfo->context)

Definition at line 41 of file windowapi.h.

◆ WINDOW_SEEK_CURRENT

#define WINDOW_SEEK_CURRENT   0

Definition at line 34 of file windowapi.h.

◆ WINDOW_SEEK_HEAD

#define WINDOW_SEEK_HEAD   1

Definition at line 35 of file windowapi.h.

◆ WINDOW_SEEK_TAIL

#define WINDOW_SEEK_TAIL   2

Definition at line 36 of file windowapi.h.

◆ WindowObjectIsValid

#define WindowObjectIsValid (   winobj)     ((winobj) != NULL && IsA(winobj, WindowObjectData))

Definition at line 43 of file windowapi.h.

Typedef Documentation

◆ WindowObject

Definition at line 39 of file windowapi.h.

Function Documentation

◆ WinCheckAndInitializeNullTreatment()

void WinCheckAndInitializeNullTreatment ( WindowObject  winobj,
bool  allowNullTreatment,
FunctionCallInfo  fcinfo 
)
extern

Definition at line 3647 of file nodeWindowAgg.c.

3650{
3651 Assert(WindowObjectIsValid(winobj));
3653 {
3654 const char *funcname = get_func_name(fcinfo->flinfo->fn_oid);
3655
3656 if (!funcname)
3657 elog(ERROR, "could not get function name");
3658 ereport(ERROR,
3660 errmsg("function %s does not allow RESPECT/IGNORE NULLS",
3661 funcname)));
3662 }
3663 else if (winobj->ignore_nulls == PARSER_IGNORE_NULLS)
3664 winobj->ignore_nulls = IGNORE_NULLS;
3665}
#define Assert(condition)
Definition c.h:1002
int errcode(int sqlerrcode)
Definition elog.c:875
#define ERROR
Definition elog.h:40
#define elog(elevel,...)
Definition elog.h:228
#define ereport(elevel,...)
Definition elog.h:152
#define funcname
char * get_func_name(Oid funcid)
Definition lsyscache.c:1922
static char * errmsg
static int fb(int x)
#define PARSER_IGNORE_NULLS
Definition primnodes.h:577
#define IGNORE_NULLS
Definition primnodes.h:579
#define NO_NULLTREATMENT
Definition primnodes.h:576
Oid fn_oid
Definition fmgr.h:59
FmgrInfo * flinfo
Definition fmgr.h:87
#define WindowObjectIsValid(winobj)
Definition windowapi.h:43

References Assert, elog, ereport, errcode(), errmsg, ERROR, fb(), FunctionCallInfoBaseData::flinfo, FmgrInfo::fn_oid, funcname, get_func_name(), WindowObjectData::ignore_nulls, IGNORE_NULLS, NO_NULLTREATMENT, PARSER_IGNORE_NULLS, and WindowObjectIsValid.

Referenced by leadlag_common(), window_cume_dist(), window_dense_rank(), window_first_value(), window_last_value(), window_nth_value(), window_ntile(), window_percent_rank(), window_rank(), and window_row_number().

◆ WinGetCurrentPosition()

int64 WinGetCurrentPosition ( WindowObject  winobj)
extern

◆ WinGetFuncArgCurrent()

Datum WinGetFuncArgCurrent ( WindowObject  winobj,
int  argno,
bool isnull 
)
extern

Definition at line 4192 of file nodeWindowAgg.c.

4193{
4194 WindowAggState *winstate;
4195 ExprContext *econtext;
4196
4197 Assert(WindowObjectIsValid(winobj));
4198 winstate = winobj->winstate;
4199
4200 econtext = winstate->ss.ps.ps_ExprContext;
4201
4202 econtext->ecxt_outertuple = winstate->ss.ss_ScanTupleSlot;
4203 return ExecEvalExpr((ExprState *) list_nth(winobj->argstates, argno),
4204 econtext, isnull);
4205}
static Datum ExecEvalExpr(ExprState *state, ExprContext *econtext, bool *isNull)
Definition executor.h:401
static void * list_nth(const List *list, int n)
Definition pg_list.h:331
TupleTableSlot * ecxt_outertuple
Definition execnodes.h:291
ExprContext * ps_ExprContext
Definition execnodes.h:1243
TupleTableSlot * ss_ScanTupleSlot
Definition execnodes.h:1665
PlanState ps
Definition execnodes.h:1662
ScanState ss
Definition execnodes.h:2532

References WindowObjectData::argstates, Assert, ExprContext::ecxt_outertuple, ExecEvalExpr(), fb(), list_nth(), ScanState::ps, PlanState::ps_ExprContext, WindowAggState::ss, ScanState::ss_ScanTupleSlot, WindowObjectIsValid, and WindowObjectData::winstate.

Referenced by leadlag_common(), window_nth_value(), and window_ntile().

◆ WinGetFuncArgInFrame()

Datum WinGetFuncArgInFrame ( WindowObject  winobj,
int  argno,
int  relpos,
int  seektype,
bool  set_mark,
bool isnull,
bool isout 
)
extern

Definition at line 3993 of file nodeWindowAgg.c.

3996{
3997 WindowAggState *winstate;
3998 ExprContext *econtext;
3999 TupleTableSlot *slot;
4000 int64 abs_pos;
4002
4003 Assert(WindowObjectIsValid(winobj));
4004 winstate = winobj->winstate;
4005 econtext = winstate->ss.ps.ps_ExprContext;
4006 slot = winstate->temp_slot_1;
4007
4008 if (winobj->ignore_nulls == IGNORE_NULLS)
4010 set_mark, isnull, isout);
4011
4012 switch (seektype)
4013 {
4015 elog(ERROR, "WINDOW_SEEK_CURRENT is not supported for WinGetFuncArgInFrame");
4016 abs_pos = mark_pos = 0; /* keep compiler quiet */
4017 break;
4018 case WINDOW_SEEK_HEAD:
4019 /* rejecting relpos < 0 is easy and simplifies code below */
4020 if (relpos < 0)
4021 goto out_of_frame;
4022 update_frameheadpos(winstate);
4023 abs_pos = winstate->frameheadpos + relpos;
4024 mark_pos = abs_pos;
4025
4026 /*
4027 * Account for exclusion option if one is active, but advance only
4028 * abs_pos not mark_pos. This prevents changes of the current
4029 * row's peer group from resulting in trying to fetch a row before
4030 * some previous mark position.
4031 *
4032 * Note that in some corner cases such as current row being
4033 * outside frame, these calculations are theoretically too simple,
4034 * but it doesn't matter because we'll end up deciding the row is
4035 * out of frame. We do not attempt to avoid fetching rows past
4036 * end of frame; that would happen in some cases anyway.
4037 */
4038 switch (winstate->frameOptions & FRAMEOPTION_EXCLUSION)
4039 {
4040 case 0:
4041 /* no adjustment needed */
4042 break;
4044 if (abs_pos >= winstate->currentpos &&
4045 winstate->currentpos >= winstate->frameheadpos)
4046 abs_pos++;
4047 break;
4049 update_grouptailpos(winstate);
4050 if (abs_pos >= winstate->groupheadpos &&
4051 winstate->grouptailpos > winstate->frameheadpos)
4052 {
4053 int64 overlapstart = Max(winstate->groupheadpos,
4054 winstate->frameheadpos);
4055
4056 abs_pos += winstate->grouptailpos - overlapstart;
4057 }
4058 break;
4060 update_grouptailpos(winstate);
4061 if (abs_pos >= winstate->groupheadpos &&
4062 winstate->grouptailpos > winstate->frameheadpos)
4063 {
4064 int64 overlapstart = Max(winstate->groupheadpos,
4065 winstate->frameheadpos);
4066
4067 if (abs_pos == overlapstart)
4068 abs_pos = winstate->currentpos;
4069 else
4070 abs_pos += winstate->grouptailpos - overlapstart - 1;
4071 }
4072 break;
4073 default:
4074 elog(ERROR, "unrecognized frame option state: 0x%x",
4075 winstate->frameOptions);
4076 break;
4077 }
4078 break;
4079 case WINDOW_SEEK_TAIL:
4080 /* rejecting relpos > 0 is easy and simplifies code below */
4081 if (relpos > 0)
4082 goto out_of_frame;
4083 update_frametailpos(winstate);
4084 abs_pos = winstate->frametailpos - 1 + relpos;
4085
4086 /*
4087 * Account for exclusion option if one is active. If there is no
4088 * exclusion, we can safely set the mark at the accessed row. But
4089 * if there is, we can only mark the frame start, because we can't
4090 * be sure how far back in the frame the exclusion might cause us
4091 * to fetch in future. Furthermore, we have to actually check
4092 * against frameheadpos here, since it's unsafe to try to fetch a
4093 * row before frame start if the mark might be there already.
4094 */
4095 switch (winstate->frameOptions & FRAMEOPTION_EXCLUSION)
4096 {
4097 case 0:
4098 /* no adjustment needed */
4099 mark_pos = abs_pos;
4100 break;
4102 if (abs_pos <= winstate->currentpos &&
4103 winstate->currentpos < winstate->frametailpos)
4104 abs_pos--;
4105 update_frameheadpos(winstate);
4106 if (abs_pos < winstate->frameheadpos)
4107 goto out_of_frame;
4108 mark_pos = winstate->frameheadpos;
4109 break;
4111 update_grouptailpos(winstate);
4112 if (abs_pos < winstate->grouptailpos &&
4113 winstate->groupheadpos < winstate->frametailpos)
4114 {
4115 int64 overlapend = Min(winstate->grouptailpos,
4116 winstate->frametailpos);
4117
4118 abs_pos -= overlapend - winstate->groupheadpos;
4119 }
4120 update_frameheadpos(winstate);
4121 if (abs_pos < winstate->frameheadpos)
4122 goto out_of_frame;
4123 mark_pos = winstate->frameheadpos;
4124 break;
4126 update_grouptailpos(winstate);
4127 if (abs_pos < winstate->grouptailpos &&
4128 winstate->groupheadpos < winstate->frametailpos)
4129 {
4130 int64 overlapend = Min(winstate->grouptailpos,
4131 winstate->frametailpos);
4132
4133 if (abs_pos == overlapend - 1)
4134 abs_pos = winstate->currentpos;
4135 else
4136 abs_pos -= overlapend - 1 - winstate->groupheadpos;
4137 }
4138 update_frameheadpos(winstate);
4139 if (abs_pos < winstate->frameheadpos)
4140 goto out_of_frame;
4141 mark_pos = winstate->frameheadpos;
4142 break;
4143 default:
4144 elog(ERROR, "unrecognized frame option state: 0x%x",
4145 winstate->frameOptions);
4146 mark_pos = 0; /* keep compiler quiet */
4147 break;
4148 }
4149 break;
4150 default:
4151 elog(ERROR, "unrecognized window seek type: %d", seektype);
4152 abs_pos = mark_pos = 0; /* keep compiler quiet */
4153 break;
4154 }
4155
4156 if (!window_gettupleslot(winobj, abs_pos, slot))
4157 goto out_of_frame;
4158
4159 /* The code above does not detect all out-of-frame cases, so check */
4160 if (row_is_in_frame(winobj, abs_pos, slot, false) <= 0)
4161 goto out_of_frame;
4162
4163 if (isout)
4164 *isout = false;
4165 if (set_mark)
4167 econtext->ecxt_outertuple = slot;
4168 return ExecEvalExpr((ExprState *) list_nth(winobj->argstates, argno),
4169 econtext, isnull);
4170
4172 if (isout)
4173 *isout = true;
4174 *isnull = true;
4175 return (Datum) 0;
4176}
#define Min(x, y)
Definition c.h:1131
#define Max(x, y)
Definition c.h:1125
int64_t int64
Definition c.h:680
static void update_grouptailpos(WindowAggState *winstate)
static Datum ignorenulls_getfuncarginframe(WindowObject winobj, int argno, int relpos, int seektype, bool set_mark, bool *isnull, bool *isout)
static bool window_gettupleslot(WindowObject winobj, int64 pos, TupleTableSlot *slot)
void WinSetMarkPosition(WindowObject winobj, int64 markpos)
static int row_is_in_frame(WindowObject winobj, int64 pos, TupleTableSlot *slot, bool fetch_tuple)
static void update_frametailpos(WindowAggState *winstate)
static void update_frameheadpos(WindowAggState *winstate)
#define FRAMEOPTION_EXCLUDE_CURRENT_ROW
Definition parsenodes.h:628
#define FRAMEOPTION_EXCLUDE_TIES
Definition parsenodes.h:630
#define FRAMEOPTION_EXCLUDE_GROUP
Definition parsenodes.h:629
#define FRAMEOPTION_EXCLUSION
Definition parsenodes.h:636
uint64_t Datum
Definition postgres.h:70
TupleTableSlot * temp_slot_1
Definition execnodes.h:2614
#define WINDOW_SEEK_TAIL
Definition windowapi.h:36
#define WINDOW_SEEK_HEAD
Definition windowapi.h:35
#define WINDOW_SEEK_CURRENT
Definition windowapi.h:34

References WindowObjectData::argstates, Assert, WindowAggState::currentpos, ExprContext::ecxt_outertuple, elog, ERROR, ExecEvalExpr(), fb(), WindowAggState::frameheadpos, FRAMEOPTION_EXCLUDE_CURRENT_ROW, FRAMEOPTION_EXCLUDE_GROUP, FRAMEOPTION_EXCLUDE_TIES, FRAMEOPTION_EXCLUSION, WindowAggState::frameOptions, WindowAggState::frametailpos, WindowAggState::groupheadpos, WindowAggState::grouptailpos, WindowObjectData::ignore_nulls, IGNORE_NULLS, ignorenulls_getfuncarginframe(), list_nth(), Max, Min, ScanState::ps, PlanState::ps_ExprContext, row_is_in_frame(), WindowAggState::ss, WindowAggState::temp_slot_1, update_frameheadpos(), update_frametailpos(), update_grouptailpos(), window_gettupleslot(), WINDOW_SEEK_CURRENT, WINDOW_SEEK_HEAD, WINDOW_SEEK_TAIL, WindowObjectIsValid, WinSetMarkPosition(), and WindowObjectData::winstate.

Referenced by window_first_value(), window_last_value(), and window_nth_value().

◆ WinGetFuncArgInPartition()

Datum WinGetFuncArgInPartition ( WindowObject  winobj,
int  argno,
int  relpos,
int  seektype,
bool  set_mark,
bool isnull,
bool isout 
)
extern

Definition at line 3820 of file nodeWindowAgg.c.

3823{
3824 WindowAggState *winstate;
3825 int64 abs_pos;
3827 Datum datum;
3828 bool null_treatment;
3829 int notnull_offset;
3830 int notnull_relpos;
3831 int forward;
3832 bool myisout;
3833 bool got_datum;
3834
3835 Assert(WindowObjectIsValid(winobj));
3836 winstate = winobj->winstate;
3837
3838 null_treatment = (winobj->ignore_nulls == IGNORE_NULLS && relpos != 0);
3839
3840 switch (seektype)
3841 {
3843 if (null_treatment)
3844 abs_pos = winstate->currentpos;
3845 else
3846 abs_pos = winstate->currentpos + relpos;
3847 break;
3848 case WINDOW_SEEK_HEAD:
3849 if (null_treatment)
3850 abs_pos = 0;
3851 else
3852 abs_pos = relpos;
3853 break;
3854 case WINDOW_SEEK_TAIL:
3855 spool_tuples(winstate, -1);
3856 abs_pos = winstate->spooled_rows - 1 + relpos;
3857 break;
3858 default:
3859 elog(ERROR, "unrecognized window seek type: %d", seektype);
3860 abs_pos = 0; /* keep compiler quiet */
3861 break;
3862 }
3863
3864 /* Easy case if IGNORE NULLS is not specified */
3865 if (!null_treatment)
3866 {
3867 /* get tuple and evaluate in partition */
3868 datum = gettuple_eval_partition(winobj, argno,
3869 abs_pos, isnull, &myisout);
3870 if (!myisout && set_mark)
3871 WinSetMarkPosition(winobj, abs_pos);
3872 if (isout)
3873 *isout = myisout;
3874 return datum;
3875 }
3876
3877 /* Prepare for loop */
3878 notnull_offset = 0;
3880 forward = relpos > 0 ? 1 : -1;
3881 myisout = false;
3882 got_datum = false;
3883 datum = 0;
3884
3885 /*
3886 * IGNORE NULLS + WINDOW_SEEK_CURRENT + relpos > 0 case, we would fetch
3887 * beyond the current row + relpos to find out the target row. If we mark
3888 * at abs_pos, next call to WinGetFuncArgInPartition or
3889 * WinGetFuncArgInFrame (in case when a window function have multiple
3890 * args) could fail with "cannot fetch row before WindowObject's mark
3891 * position". So keep the mark position at currentpos.
3892 */
3893 if (seektype == WINDOW_SEEK_CURRENT && relpos > 0)
3894 mark_pos = winstate->currentpos;
3895 else
3896 {
3897 /*
3898 * For other cases we have no idea what position of row callers would
3899 * fetch next time. Also for relpos < 0 case (we go backward), we
3900 * cannot set mark either. For those cases we always set mark at 0.
3901 */
3902 mark_pos = 0;
3903 }
3904
3905 /*
3906 * Get the next nonnull value in the partition, moving forward or backward
3907 * until we find a value or reach the partition's end. We cache the
3908 * nullness status because we may repeat this process many times.
3909 */
3910 do
3911 {
3912 int nn_info; /* NOT NULL status */
3913
3914 abs_pos += forward;
3915 if (abs_pos < 0) /* clearly out of partition */
3916 break;
3917
3918 /* check NOT NULL cached info */
3920 if (nn_info == NN_NOTNULL) /* this row is known to be NOT NULL */
3922 else if (nn_info == NN_NULL) /* this row is known to be NULL */
3923 continue; /* keep on moving forward or backward */
3924 else /* need to check NULL or not */
3925 {
3926 /*
3927 * NOT NULL info does not exist yet. Get tuple and evaluate func
3928 * arg in partition. Keep the return value in case this row is the
3929 * target; re-evaluating a volatile argument could give a
3930 * different nullness status.
3931 */
3932 datum = gettuple_eval_partition(winobj, argno,
3933 abs_pos, isnull, &myisout);
3934 if (myisout) /* out of partition? */
3935 break;
3936 if (!*isnull)
3937 {
3940 got_datum = true;
3941 }
3942 /* record the row status */
3943 put_notnull_info(winobj, abs_pos, argno, *isnull);
3944 }
3945 } while (notnull_offset < notnull_relpos);
3946
3947 /* get tuple and evaluate func arg in partition */
3948 if (!got_datum)
3949 datum = gettuple_eval_partition(winobj, argno,
3950 abs_pos, isnull, &myisout);
3951 if (!myisout && set_mark)
3953 if (isout)
3954 *isout = myisout;
3955
3956 return datum;
3957}
static void spool_tuples(WindowAggState *winstate, int64 pos)
#define NN_NOTNULL
static void put_notnull_info(WindowObject winobj, int64 pos, int argno, bool isnull)
#define NN_NULL
static uint8 get_notnull_info(WindowObject winobj, int64 pos, int argno)
static Datum gettuple_eval_partition(WindowObject winobj, int argno, int64 abs_pos, bool *isnull, bool *isout)

References Assert, WindowAggState::currentpos, elog, ERROR, fb(), get_notnull_info(), gettuple_eval_partition(), WindowObjectData::ignore_nulls, IGNORE_NULLS, NN_NOTNULL, NN_NULL, put_notnull_info(), spool_tuples(), WindowAggState::spooled_rows, WINDOW_SEEK_CURRENT, WINDOW_SEEK_HEAD, WINDOW_SEEK_TAIL, WindowObjectIsValid, WinSetMarkPosition(), and WindowObjectData::winstate.

Referenced by leadlag_common().

◆ WinGetPartitionLocalMemory()

void * WinGetPartitionLocalMemory ( WindowObject  winobj,
Size  sz 
)
extern

Definition at line 3680 of file nodeWindowAgg.c.

3681{
3682 Assert(WindowObjectIsValid(winobj));
3683 if (winobj->localmem == NULL)
3684 winobj->localmem =
3686 return winobj->localmem;
3687}
void * MemoryContextAllocZero(MemoryContext context, Size size)
Definition mcxt.c:1269
MemoryContext partcontext
Definition execnodes.h:2589

References Assert, fb(), WindowObjectData::localmem, MemoryContextAllocZero(), WindowAggState::partcontext, WindowObjectIsValid, and WindowObjectData::winstate.

Referenced by rank_up(), window_cume_dist(), window_dense_rank(), window_ntile(), window_percent_rank(), and window_rank().

◆ WinGetPartitionRowCount()

int64 WinGetPartitionRowCount ( WindowObject  winobj)
extern

Definition at line 3710 of file nodeWindowAgg.c.

3711{
3712 Assert(WindowObjectIsValid(winobj));
3713 spool_tuples(winobj->winstate, -1);
3714 return winobj->winstate->spooled_rows;
3715}

References Assert, spool_tuples(), WindowAggState::spooled_rows, WindowObjectIsValid, and WindowObjectData::winstate.

Referenced by window_cume_dist(), window_ntile(), and window_percent_rank().

◆ WinRowsArePeers()

bool WinRowsArePeers ( WindowObject  winobj,
int64  pos1,
int64  pos2 
)
extern

Definition at line 3763 of file nodeWindowAgg.c.

3764{
3765 WindowAggState *winstate;
3766 WindowAgg *node;
3769 bool res;
3770
3771 Assert(WindowObjectIsValid(winobj));
3772 winstate = winobj->winstate;
3773 node = (WindowAgg *) winstate->ss.ps.plan;
3774
3775 /* If no ORDER BY, all rows are peers; don't bother to fetch them */
3776 if (node->ordNumCols == 0)
3777 return true;
3778
3779 /*
3780 * Note: OK to use temp_slot_2 here because we aren't calling any
3781 * frame-related functions (those tend to clobber temp_slot_2).
3782 */
3783 slot1 = winstate->temp_slot_1;
3784 slot2 = winstate->temp_slot_2;
3785
3786 if (!window_gettupleslot(winobj, pos1, slot1))
3787 elog(ERROR, "specified position is out of window: " INT64_FORMAT,
3788 pos1);
3789 if (!window_gettupleslot(winobj, pos2, slot2))
3790 elog(ERROR, "specified position is out of window: " INT64_FORMAT,
3791 pos2);
3792
3793 res = are_peers(winstate, slot1, slot2);
3794
3797
3798 return res;
3799}
#define INT64_FORMAT
Definition c.h:693
static bool are_peers(WindowAggState *winstate, TupleTableSlot *slot1, TupleTableSlot *slot2)
Plan * plan
Definition execnodes.h:1202
TupleTableSlot * temp_slot_2
Definition execnodes.h:2615
int ordNumCols
Definition plannodes.h:1276
static TupleTableSlot * ExecClearTuple(TupleTableSlot *slot)
Definition tuptable.h:476

References are_peers(), Assert, elog, ERROR, ExecClearTuple(), fb(), INT64_FORMAT, WindowAgg::ordNumCols, PlanState::plan, ScanState::ps, WindowAggState::ss, WindowAggState::temp_slot_1, WindowAggState::temp_slot_2, window_gettupleslot(), WindowObjectIsValid, and WindowObjectData::winstate.

Referenced by rank_up(), and window_cume_dist().

◆ WinSetMarkPosition()

void WinSetMarkPosition ( WindowObject  winobj,
int64  markpos 
)
extern

Definition at line 3728 of file nodeWindowAgg.c.

3729{
3730 WindowAggState *winstate;
3731
3732 Assert(WindowObjectIsValid(winobj));
3733 winstate = winobj->winstate;
3734
3735 if (markpos < winobj->markpos)
3736 elog(ERROR, "cannot move WindowObject's mark position backward");
3737 tuplestore_select_read_pointer(winstate->buffer, winobj->markptr);
3738 if (markpos > winobj->markpos)
3739 {
3740 tuplestore_skiptuples(winstate->buffer,
3741 markpos - winobj->markpos,
3742 true);
3743 winobj->markpos = markpos;
3744 }
3745 tuplestore_select_read_pointer(winstate->buffer, winobj->readptr);
3746 if (markpos > winobj->seekpos)
3747 {
3748 tuplestore_skiptuples(winstate->buffer,
3749 markpos - winobj->seekpos,
3750 true);
3751 winobj->seekpos = markpos;
3752 }
3753}
Tuplestorestate * buffer
Definition execnodes.h:2543
void tuplestore_select_read_pointer(Tuplestorestate *state, int ptr)
Definition tuplestore.c:508
bool tuplestore_skiptuples(Tuplestorestate *state, int64 ntuples, bool forward)

References Assert, WindowAggState::buffer, elog, ERROR, fb(), WindowObjectData::markpos, WindowObjectData::markptr, WindowObjectData::readptr, WindowObjectData::seekpos, tuplestore_select_read_pointer(), tuplestore_skiptuples(), WindowObjectIsValid, and WindowObjectData::winstate.

Referenced by eval_windowaggregates(), ignorenulls_getfuncarginframe(), rank_up(), window_row_number(), WinGetFuncArgInFrame(), and WinGetFuncArgInPartition().