Header And Logo

PostgreSQL
| The world's most advanced open source database.

Defines | Typedefs | Functions

windowapi.h File Reference

This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Defines

#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 * WinGetPartitionLocalMemory (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)

Define Documentation

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

Definition at line 32 of file windowapi.h.

Referenced by leadlag_common(), WinGetFuncArgInFrame(), and WinGetFuncArgInPartition().

#define WINDOW_SEEK_HEAD   1
#define WINDOW_SEEK_TAIL   2

Definition at line 34 of file windowapi.h.

Referenced by window_last_value(), WinGetFuncArgInFrame(), and WinGetFuncArgInPartition().

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

Typedef Documentation

typedef struct WindowObjectData* WindowObject

Definition at line 37 of file windowapi.h.


Function Documentation

int64 WinGetCurrentPosition ( WindowObject  winobj  ) 
Datum WinGetFuncArgCurrent ( WindowObject  winobj,
int  argno,
bool isnull 
)
Datum WinGetFuncArgInFrame ( WindowObject  winobj,
int  argno,
int  relpos,
int  seektype,
bool  set_mark,
bool isnull,
bool isout 
)

Definition at line 2211 of file nodeWindowAgg.c.

References WindowObjectData::argstates, Assert, WindowAggState::currentpos, ExprContext::ecxt_outertuple, elog, ERROR, ExecEvalExpr, WindowAggState::frameheadpos, FRAMEOPTION_RANGE, FRAMEOPTION_START_UNBOUNDED_PRECEDING, WindowAggState::frameOptions, WindowAggState::frametailpos, list_nth(), NULL, ScanState::ps, PlanState::ps_ExprContext, row_is_in_frame(), WindowAggState::ss, WindowAggState::temp_slot_1, WindowAggState::temp_slot_2, update_frameheadpos(), update_frametailpos(), 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().

{
    WindowAggState *winstate;
    ExprContext *econtext;
    TupleTableSlot *slot;
    bool        gottuple;
    int64       abs_pos;

    Assert(WindowObjectIsValid(winobj));
    winstate = winobj->winstate;
    econtext = winstate->ss.ps.ps_ExprContext;
    slot = winstate->temp_slot_1;

    switch (seektype)
    {
        case WINDOW_SEEK_CURRENT:
            abs_pos = winstate->currentpos + relpos;
            break;
        case WINDOW_SEEK_HEAD:
            update_frameheadpos(winobj, slot);
            abs_pos = winstate->frameheadpos + relpos;
            break;
        case WINDOW_SEEK_TAIL:
            update_frametailpos(winobj, slot);
            abs_pos = winstate->frametailpos + relpos;
            break;
        default:
            elog(ERROR, "unrecognized window seek type: %d", seektype);
            abs_pos = 0;        /* keep compiler quiet */
            break;
    }

    gottuple = window_gettupleslot(winobj, abs_pos, slot);
    if (gottuple)
        gottuple = row_is_in_frame(winstate, abs_pos, slot);

    if (!gottuple)
    {
        if (isout)
            *isout = true;
        *isnull = true;
        return (Datum) 0;
    }
    else
    {
        if (isout)
            *isout = false;
        if (set_mark)
        {
            int         frameOptions = winstate->frameOptions;
            int64       mark_pos = abs_pos;

            /*
             * In RANGE mode with a moving frame head, we must not let the
             * mark advance past frameheadpos, since that row has to be
             * fetchable during future update_frameheadpos calls.
             *
             * XXX it is very ugly to pollute window functions' marks with
             * this consideration; it could for instance mask a logic bug that
             * lets a window function fetch rows before what it had claimed
             * was its mark.  Perhaps use a separate mark for frame head
             * probes?
             */
            if ((frameOptions & FRAMEOPTION_RANGE) &&
                !(frameOptions & FRAMEOPTION_START_UNBOUNDED_PRECEDING))
            {
                update_frameheadpos(winobj, winstate->temp_slot_2);
                if (mark_pos > winstate->frameheadpos)
                    mark_pos = winstate->frameheadpos;
            }
            WinSetMarkPosition(winobj, mark_pos);
        }
        econtext->ecxt_outertuple = slot;
        return ExecEvalExpr((ExprState *) list_nth(winobj->argstates, argno),
                            econtext, isnull, NULL);
    }
}

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

Definition at line 2115 of file nodeWindowAgg.c.

References WindowObjectData::argstates, Assert, WindowAggState::currentpos, ExprContext::ecxt_outertuple, elog, ERROR, ExecEvalExpr, WindowAggState::frameheadpos, FRAMEOPTION_RANGE, FRAMEOPTION_START_UNBOUNDED_PRECEDING, WindowAggState::frameOptions, list_nth(), NULL, ScanState::ps, PlanState::ps_ExprContext, spool_tuples(), WindowAggState::spooled_rows, WindowAggState::ss, WindowAggState::temp_slot_1, WindowAggState::temp_slot_2, update_frameheadpos(), window_gettupleslot(), WINDOW_SEEK_CURRENT, WINDOW_SEEK_HEAD, WINDOW_SEEK_TAIL, WindowObjectIsValid, WinSetMarkPosition(), and WindowObjectData::winstate.

Referenced by leadlag_common().

{
    WindowAggState *winstate;
    ExprContext *econtext;
    TupleTableSlot *slot;
    bool        gottuple;
    int64       abs_pos;

    Assert(WindowObjectIsValid(winobj));
    winstate = winobj->winstate;
    econtext = winstate->ss.ps.ps_ExprContext;
    slot = winstate->temp_slot_1;

    switch (seektype)
    {
        case WINDOW_SEEK_CURRENT:
            abs_pos = winstate->currentpos + relpos;
            break;
        case WINDOW_SEEK_HEAD:
            abs_pos = relpos;
            break;
        case WINDOW_SEEK_TAIL:
            spool_tuples(winstate, -1);
            abs_pos = winstate->spooled_rows - 1 + relpos;
            break;
        default:
            elog(ERROR, "unrecognized window seek type: %d", seektype);
            abs_pos = 0;        /* keep compiler quiet */
            break;
    }

    gottuple = window_gettupleslot(winobj, abs_pos, slot);

    if (!gottuple)
    {
        if (isout)
            *isout = true;
        *isnull = true;
        return (Datum) 0;
    }
    else
    {
        if (isout)
            *isout = false;
        if (set_mark)
        {
            int         frameOptions = winstate->frameOptions;
            int64       mark_pos = abs_pos;

            /*
             * In RANGE mode with a moving frame head, we must not let the
             * mark advance past frameheadpos, since that row has to be
             * fetchable during future update_frameheadpos calls.
             *
             * XXX it is very ugly to pollute window functions' marks with
             * this consideration; it could for instance mask a logic bug that
             * lets a window function fetch rows before what it had claimed
             * was its mark.  Perhaps use a separate mark for frame head
             * probes?
             */
            if ((frameOptions & FRAMEOPTION_RANGE) &&
                !(frameOptions & FRAMEOPTION_START_UNBOUNDED_PRECEDING))
            {
                update_frameheadpos(winobj, winstate->temp_slot_2);
                if (mark_pos > winstate->frameheadpos)
                    mark_pos = winstate->frameheadpos;
            }
            WinSetMarkPosition(winobj, mark_pos);
        }
        econtext->ecxt_outertuple = slot;
        return ExecEvalExpr((ExprState *) list_nth(winobj->argstates, argno),
                            econtext, isnull, NULL);
    }
}

void* WinGetPartitionLocalMemory ( WindowObject  winobj,
Size  sz 
)
int64 WinGetPartitionRowCount ( WindowObject  winobj  ) 
bool WinRowsArePeers ( WindowObject  winobj,
int64  pos1,
int64  pos2 
)

Definition at line 2062 of file nodeWindowAgg.c.

References are_peers(), Assert, elog, ERROR, ExecClearTuple(), 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().

{
    WindowAggState *winstate;
    WindowAgg  *node;
    TupleTableSlot *slot1;
    TupleTableSlot *slot2;
    bool        res;

    Assert(WindowObjectIsValid(winobj));
    winstate = winobj->winstate;
    node = (WindowAgg *) winstate->ss.ps.plan;

    /* If no ORDER BY, all rows are peers; don't bother to fetch them */
    if (node->ordNumCols == 0)
        return true;

    slot1 = winstate->temp_slot_1;
    slot2 = winstate->temp_slot_2;

    if (!window_gettupleslot(winobj, pos1, slot1))
        elog(ERROR, "specified position is out of window: " INT64_FORMAT,
             pos1);
    if (!window_gettupleslot(winobj, pos2, slot2))
        elog(ERROR, "specified position is out of window: " INT64_FORMAT,
             pos2);

    res = are_peers(winstate, slot1, slot2);

    ExecClearTuple(slot1);
    ExecClearTuple(slot2);

    return res;
}

void WinSetMarkPosition ( WindowObject  winobj,
int64  markpos 
)

Definition at line 2031 of file nodeWindowAgg.c.

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

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

{
    WindowAggState *winstate;

    Assert(WindowObjectIsValid(winobj));
    winstate = winobj->winstate;

    if (markpos < winobj->markpos)
        elog(ERROR, "cannot move WindowObject's mark position backward");
    tuplestore_select_read_pointer(winstate->buffer, winobj->markptr);
    while (markpos > winobj->markpos)
    {
        tuplestore_advance(winstate->buffer, true);
        winobj->markpos++;
    }
    tuplestore_select_read_pointer(winstate->buffer, winobj->readptr);
    while (markpos > winobj->seekpos)
    {
        tuplestore_advance(winstate->buffer, true);
        winobj->seekpos++;
    }
}