aboutsummaryrefslogtreecommitdiff
path: root/src/interfaces/ecpg/ecpglib/prepare.c
diff options
context:
space:
mode:
authorMichael Meskes <meskes@postgresql.org>2019-05-22 04:58:29 +0200
committerMichael Meskes <meskes@postgresql.org>2019-05-22 04:58:29 +0200
commita1dc6ab465986a62b308dd1bb8da316b5ed9685a (patch)
treee7ca21165238a726731a69e7fb1e50e77c51263f /src/interfaces/ecpg/ecpglib/prepare.c
parent5af2e976d72aa345337596cc986237c57e1146b2 (diff)
downloadpostgresql-a1dc6ab465986a62b308dd1bb8da316b5ed9685a.tar.gz
postgresql-a1dc6ab465986a62b308dd1bb8da316b5ed9685a.zip
Implement PREPARE AS statement for ECPG.
Besides implementing the new statement this change fix some issues with the parsing of PREPARE and EXECUTE statements. The different forms of these statements are now all handled in a ujnified way. Author: Matsumura-san <matsumura.ryo@jp.fujitsu.com>
Diffstat (limited to 'src/interfaces/ecpg/ecpglib/prepare.c')
-rw-r--r--src/interfaces/ecpg/ecpglib/prepare.c54
1 files changed, 54 insertions, 0 deletions
diff --git a/src/interfaces/ecpg/ecpglib/prepare.c b/src/interfaces/ecpg/ecpglib/prepare.c
index 0ef85c9de18..83de5e88b1e 100644
--- a/src/interfaces/ecpg/ecpglib/prepare.c
+++ b/src/interfaces/ecpg/ecpglib/prepare.c
@@ -56,6 +56,60 @@ isvarchar(unsigned char c)
return false;
}
+bool
+ecpg_register_prepared_stmt(struct statement *stmt)
+{
+ struct statement *prep_stmt;
+ struct prepared_statement *this;
+ struct connection *con = NULL;
+ struct prepared_statement *prev = NULL;
+ char *real_connection_name;
+ int lineno = stmt->lineno;
+
+ real_connection_name = ecpg_get_con_name_by_declared_name(stmt->name);
+ if (real_connection_name == NULL)
+ real_connection_name = stmt->connection->name;
+
+ con = ecpg_get_connection(real_connection_name);
+ if (!ecpg_init(con, real_connection_name, stmt->lineno))
+ return false;
+
+ /* check if we already have prepared this statement */
+ this = ecpg_find_prepared_statement(stmt->name, con, &prev);
+ if (this && !deallocate_one(lineno, ECPG_COMPAT_PGSQL, con, prev, this))
+ return false;
+
+ /* allocate new statement */
+ this = (struct prepared_statement *) ecpg_alloc(sizeof(struct prepared_statement), lineno);
+ if (!this)
+ return false;
+
+ prep_stmt = (struct statement *) ecpg_alloc(sizeof(struct statement), lineno);
+ if (!stmt)
+ {
+ ecpg_free(this);
+ return false;
+ }
+ memset(prep_stmt, 0, sizeof(struct statement));
+
+ /* create statement */
+ prep_stmt->lineno = lineno;
+ prep_stmt->connection = con;
+ prep_stmt->command = ecpg_strdup(stmt->command, lineno);
+ prep_stmt->inlist = prep_stmt->outlist = NULL;
+ this->name = ecpg_strdup(stmt->name, lineno);
+ this->stmt = prep_stmt;
+ this->prepared = true;
+
+ if (con->prep_stmts == NULL)
+ this->next = NULL;
+ else
+ this->next = con->prep_stmts;
+
+ con->prep_stmts = this;
+ return true;
+}
+
static bool
replace_variables(char **text, int lineno)
{