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

Go to the source code of this file.

Functions

void pgpa_output_advice (StringInfo buf, pgpa_plan_walker_context *walker, pgpa_identifier *rt_identifiers)
 

Function Documentation

◆ pgpa_output_advice()

void pgpa_output_advice ( StringInfo  buf,
pgpa_plan_walker_context walker,
pgpa_identifier rt_identifiers 
)
extern

Definition at line 80 of file pgpa_output.c.

82{
83 Index rtable_length = list_length(walker->pstmt->rtable);
84 ListCell *lc;
85 pgpa_output_context context;
86
87 /* Basic initialization. */
88 memset(&context, 0, sizeof(pgpa_output_context));
89 context.buf = buf;
90
91 /*
92 * Convert identifiers to string form. Note that the loop variable here is
93 * not an RTI, because RTIs are 1-based. Some RTIs will have no
94 * identifier, either because the reloptkind is RTE_JOIN or because that
95 * portion of the query didn't make it into the final plan.
96 */
97 context.rid_strings = palloc0_array(const char *, rtable_length);
98 for (int i = 0; i < rtable_length; ++i)
99 if (rt_identifiers[i].alias_name != NULL)
101
102 /*
103 * If the user chooses to use EXPLAIN (PLAN_ADVICE) in an 80-column window
104 * from a psql client with default settings, psql will add one space to
105 * the left of the output and EXPLAIN will add two more to the left of the
106 * advice. Thus, lines of more than 77 characters will wrap. We set the
107 * wrap limit to 76 here so that the output won't reach all the way to the
108 * very last column of the terminal.
109 *
110 * Of course, this is fairly arbitrary set of assumptions, and one could
111 * well make an argument for a different wrap limit, or for a configurable
112 * one.
113 */
114 context.wrap_column = 76;
115
116 /*
117 * Each piece of JOIN_ORDER() advice fully describes the join order for a
118 * a single unrolled join. Merging is not permitted, because that would
119 * change the meaning, e.g. SEQ_SCAN(a b c d) means simply that sequential
120 * scans should be used for all of those relations, and is thus equivalent
121 * to SEQ_SCAN(a b) SEQ_SCAN(c d), but JOIN_ORDER(a b c d) means that "a"
122 * is the driving table which is then joined to "b" then "c" then "d",
123 * which is totally different from JOIN_ORDER(a b) and JOIN_ORDER(c d).
124 */
125 foreach(lc, walker->toplevel_unrolled_joins)
126 {
128
129 if (buf->len > 0)
131 appendStringInfo(context.buf, "JOIN_ORDER(");
133 appendStringInfoChar(context.buf, ')');
134 pgpa_maybe_linebreak(context.buf, context.wrap_column);
135 }
136
137 /* Emit join strategy advice. */
138 for (int s = 0; s < NUM_PGPA_JOIN_STRATEGY; ++s)
139 {
140 char *strategy = pgpa_cstring_join_strategy(s);
141
143 strategy,
144 walker->join_strategies[s]);
145 }
146
147 /*
148 * Emit scan strategy advice (but not for ordinary scans, which are
149 * definitionally uninteresting).
150 */
151 for (int c = 0; c < NUM_PGPA_SCAN_STRATEGY; ++c)
152 if (c != PGPA_SCAN_ORDINARY)
153 pgpa_output_scan_strategy(&context, c, walker->scans[c]);
154
155 /* Emit query feature advice. */
156 for (int t = 0; t < NUM_PGPA_QF_TYPES; ++t)
157 pgpa_output_query_feature(&context, t, walker->query_features[t]);
158
159 /* Emit NO_GATHER advice. */
160 pgpa_output_no_gather(&context, walker->no_gather_scans);
161
162 /* Emit DO_NOT_SCAN advice. */
163 pgpa_output_do_not_scan(&context, walker->do_not_scan_identifiers);
164}
unsigned int Index
Definition c.h:698
#define palloc0_array(type, count)
Definition fe_memutils.h:77
int i
Definition isn.c:77
#define lfirst(lc)
Definition pg_list.h:172
static int list_length(const List *l)
Definition pg_list.h:152
static char buf[DEFAULT_XLOG_SEG_SIZE]
const char * pgpa_identifier_string(const pgpa_identifier *rid)
#define NUM_PGPA_JOIN_STRATEGY
Definition pgpa_join.h:38
static void pgpa_output_simple_strategy(pgpa_output_context *context, char *strategy, List *relid_sets)
static char * pgpa_cstring_join_strategy(pgpa_join_strategy strategy)
static void pgpa_output_no_gather(pgpa_output_context *context, Bitmapset *relids)
static void pgpa_maybe_linebreak(StringInfo buf, int wrap_column)
static void pgpa_output_unrolled_join(pgpa_output_context *context, pgpa_unrolled_join *join)
static void pgpa_output_scan_strategy(pgpa_output_context *context, pgpa_scan_strategy strategy, List *scans)
static void pgpa_output_query_feature(pgpa_output_context *context, pgpa_qf_type type, List *query_features)
static void pgpa_output_do_not_scan(pgpa_output_context *context, List *identifiers)
@ PGPA_SCAN_ORDINARY
Definition pgpa_scan.h:57
#define NUM_PGPA_SCAN_STRATEGY
Definition pgpa_scan.h:68
#define NUM_PGPA_QF_TYPES
Definition pgpa_walker.h:52
char * c
static int fb(int x)
void appendStringInfo(StringInfo str, const char *fmt,...)
Definition stringinfo.c:145
void appendStringInfoChar(StringInfo str, char ch)
Definition stringinfo.c:242
const char ** rid_strings
Definition pgpa_output.c:36

References appendStringInfo(), appendStringInfoChar(), pgpa_output_context::buf, buf, fb(), i, lfirst, list_length(), NUM_PGPA_JOIN_STRATEGY, NUM_PGPA_QF_TYPES, NUM_PGPA_SCAN_STRATEGY, palloc0_array, pgpa_cstring_join_strategy(), pgpa_identifier_string(), pgpa_maybe_linebreak(), pgpa_output_do_not_scan(), pgpa_output_no_gather(), pgpa_output_query_feature(), pgpa_output_scan_strategy(), pgpa_output_simple_strategy(), pgpa_output_unrolled_join(), PGPA_SCAN_ORDINARY, pgpa_output_context::rid_strings, and pgpa_output_context::wrap_column.

Referenced by pgpa_planner_shutdown().