PostgreSQL Source Code git master
Loading...
Searching...
No Matches
test_plan_advice.c File Reference
#include "postgres.h"
#include "access/xact.h"
#include "fmgr.h"
#include "optimizer/optimizer.h"
#include "pg_plan_advice.h"
#include "utils/guc.h"
Include dependency graph for test_plan_advice.c:

Go to the source code of this file.

Functions

static chartest_plan_advice_advisor (PlannerGlobal *glob, Query *parse, const char *query_string, int cursorOptions, ExplainState *es)
 
static DefElemfind_defelem_by_defname (List *deflist, char *defname)
 
void _PG_init (void)
 

Variables

 PG_MODULE_MAGIC
 
static bool in_recursion = false
 

Function Documentation

◆ _PG_init()

void _PG_init ( void  )

Definition at line 42 of file test_plan_advice.c.

43{
45
46 /*
47 * Ask pg_plan_advice to get advice strings from test_plan_advice_advisor
48 */
50 load_external_function("pg_plan_advice", "pg_plan_advice_add_advisor",
51 true, NULL);
52
53 (*add_advisor_fn) (test_plan_advice_advisor);
54}
void * load_external_function(const char *filename, const char *funcname, bool signalNotFound, void **filehandle)
Definition dfmgr.c:95
char *(* pg_plan_advice_advisor_hook)(PlannerGlobal *glob, Query *parse, const char *query_string, int cursorOptions, ExplainState *es)
static int fb(int x)
static char * test_plan_advice_advisor(PlannerGlobal *glob, Query *parse, const char *query_string, int cursorOptions, ExplainState *es)

References fb(), load_external_function(), and test_plan_advice_advisor().

◆ find_defelem_by_defname()

static DefElem * find_defelem_by_defname ( List deflist,
char defname 
)
static

Definition at line 134 of file test_plan_advice.c.

135{
137 {
138 if (strcmp(item->defname, defname) == 0)
139 return item;
140 }
141
142 return NULL;
143}
#define foreach_node(type, var, lst)
Definition pg_list.h:496

References fb(), and foreach_node.

Referenced by test_plan_advice_advisor().

◆ test_plan_advice_advisor()

static char * test_plan_advice_advisor ( PlannerGlobal glob,
Query parse,
const char query_string,
int  cursorOptions,
ExplainState es 
)
static

Definition at line 61 of file test_plan_advice.c.

64{
65 PlannedStmt *pstmt;
66 int save_nestlevel = 0;
69
70 /*
71 * Since this function is called from the planner and triggers planning,
72 * we need a recursion guard.
73 */
74 if (in_recursion)
75 return NULL;
76
77 PG_TRY();
78 {
79 in_recursion = true;
80
81 /*
82 * Planning can trigger expression evaluation, which can result in
83 * sending NOTICE messages or other output to the client. To avoid
84 * that, we set client_min_messages = ERROR in the hopes of getting
85 * the same output with and without this module.
86 *
87 * We also need to set pg_plan_advice.always_store_advice_details so
88 * that pg_plan_advice will generate an advice string, since the whole
89 * point of this function is to get access to that.
90 */
91 save_nestlevel = NewGUCNestLevel();
92 set_config_option("client_min_messages", "error",
94 GUC_ACTION_SAVE, true, 0, false);
95 set_config_option("pg_plan_advice.always_store_advice_details", "true",
97 GUC_ACTION_SAVE, true, 0, false);
98
99 /*
100 * Replan. We must copy the Query, because the planner modifies it.
101 * (As noted elsewhere, that's unfortunate; perhaps it will be fixed
102 * some day.)
103 */
104 pstmt = planner(copyObject(parse), query_string, cursorOptions,
105 glob->boundParams, es);
106 }
107 PG_FINALLY();
108 {
109 in_recursion = false;
110 }
111 PG_END_TRY();
112
113 /* Roll back any GUC changes */
114 if (save_nestlevel > 0)
115 AtEOXact_GUC(false, save_nestlevel);
116
117 /* Extract and return the advice string */
119 "pg_plan_advice");
120 if (pgpa_item == NULL)
121 elog(ERROR, "extension state for pg_plan_advice not found");
123 "advice_string");
125 elog(ERROR,
126 "advice string for pg_plan_advice not found in extension state");
127 return strVal(advice_string_item->arg);
128}
#define PG_TRY(...)
Definition elog.h:372
#define PG_END_TRY(...)
Definition elog.h:397
#define ERROR
Definition elog.h:39
#define elog(elevel,...)
Definition elog.h:226
#define PG_FINALLY(...)
Definition elog.h:389
int NewGUCNestLevel(void)
Definition guc.c:2142
void AtEOXact_GUC(bool isCommit, int nestLevel)
Definition guc.c:2169
int set_config_option(const char *name, const char *value, GucContext context, GucSource source, GucAction action, bool changeVal, int elevel, bool is_reload)
Definition guc.c:3248
@ GUC_ACTION_SAVE
Definition guc.h:205
@ PGC_S_SESSION
Definition guc.h:126
@ PGC_SUSET
Definition guc.h:78
#define copyObject(obj)
Definition nodes.h:232
PlannedStmt * planner(Query *parse, const char *query_string, int cursorOptions, ParamListInfo boundParams, ExplainState *es)
Definition planner.c:315
Definition pg_list.h:54
List * extension_state
Definition plannodes.h:163
static DefElem * find_defelem_by_defname(List *deflist, char *defname)
static bool in_recursion
#define strVal(v)
Definition value.h:82

References AtEOXact_GUC(), copyObject, elog, ERROR, PlannedStmt::extension_state, fb(), find_defelem_by_defname(), GUC_ACTION_SAVE, in_recursion, NewGUCNestLevel(), parse(), PG_END_TRY, PG_FINALLY, PG_TRY, PGC_S_SESSION, PGC_SUSET, planner(), set_config_option(), and strVal.

Referenced by _PG_init().

Variable Documentation

◆ in_recursion

bool in_recursion = false
static

Definition at line 29 of file test_plan_advice.c.

Referenced by test_plan_advice_advisor().

◆ PG_MODULE_MAGIC

PG_MODULE_MAGIC

Definition at line 27 of file test_plan_advice.c.