Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse files

Add quoteName() method with MySQL, SQLite, PgSQL, Firebird, Oracle an…

…d MS SQL implementations
  • Loading branch information...
commit b417336e69a385d3f171e3afe145a9e3af3c0cc3 1 parent 75cf51d
@vrana vrana authored vrana committed
View
34 ext/pdo/pdo_dbh.c
@@ -1185,6 +1185,35 @@ static PHP_METHOD(PDO, quote)
}
/* }}} */
+/* {{{ proto string PDO::quoteName(string identifier)
+ Quotes string for use as a table or column name. */
+static PHP_METHOD(PDO, quoteName)
+{
+ pdo_dbh_t *dbh = zend_object_store_get_object(getThis() TSRMLS_CC);
+ char *str;
+ int str_len;
+ char *qstr;
+ int qlen;
+
+ if (FAILURE == zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &str, &str_len)) {
+ RETURN_FALSE;
+ }
+
+ PDO_DBH_CLEAR_ERR();
+ PDO_CONSTRUCT_CHECK;
+ if (!dbh->methods->name_quoter) {
+ pdo_raise_impl_error(dbh, NULL, "IM001", "driver does not support name quoting" TSRMLS_CC);
+ RETURN_FALSE;
+ }
+
+ if (dbh->methods->name_quoter(dbh, str, str_len, &qstr, &qlen TSRMLS_CC)) {
+ RETURN_STRINGL(qstr, qlen, 0);
+ }
+ PDO_HANDLE_DBH_ERR();
+ RETURN_FALSE;
+}
+/* }}} */
+
/* {{{ proto int PDO::__wakeup()
Prevents use of a PDO instance that has been unserialized */
static PHP_METHOD(PDO, __wakeup)
@@ -1257,6 +1286,10 @@ ZEND_BEGIN_ARG_INFO_EX(arginfo_pdo_quote, 0, 0, 1)
ZEND_ARG_INFO(0, paramtype)
ZEND_END_ARG_INFO()
+ZEND_BEGIN_ARG_INFO_EX(arginfo_pdo_quotename, 0, 0, 1)
+ ZEND_ARG_INFO(0, identifier)
+ZEND_END_ARG_INFO()
+
ZEND_BEGIN_ARG_INFO(arginfo_pdo__void, 0)
ZEND_END_ARG_INFO()
/* }}} */
@@ -1276,6 +1309,7 @@ const zend_function_entry pdo_dbh_functions[] = {
PHP_ME(PDO, errorInfo, arginfo_pdo__void, ZEND_ACC_PUBLIC)
PHP_ME(PDO, getAttribute, arginfo_pdo_getattribute, ZEND_ACC_PUBLIC)
PHP_ME(PDO, quote, arginfo_pdo_quote, ZEND_ACC_PUBLIC)
+ PHP_ME(PDO, quoteName, arginfo_pdo_quotename, ZEND_ACC_PUBLIC)
PHP_ME(PDO, __wakeup, arginfo_pdo__void, ZEND_ACC_PUBLIC|ZEND_ACC_FINAL)
PHP_ME(PDO, __sleep, arginfo_pdo__void, ZEND_ACC_PUBLIC|ZEND_ACC_FINAL)
PHP_ME(PDO, getAvailableDrivers, arginfo_pdo__void, ZEND_ACC_PUBLIC|ZEND_ACC_STATIC)
View
4 ext/pdo/php_pdo_driver.h
@@ -250,6 +250,9 @@ typedef long (*pdo_dbh_do_func)(pdo_dbh_t *dbh, const char *sql, long sql_len TS
/* quote a string */
typedef int (*pdo_dbh_quote_func)(pdo_dbh_t *dbh, const char *unquoted, int unquotedlen, char **quoted, int *quotedlen, enum pdo_param_type paramtype TSRMLS_DC);
+/* quote an identifier */
+typedef int (*pdo_dbh_quote_name_func)(pdo_dbh_t *dbh, const char *unquoted, int unquotedlen, char **quoted, int *quotedlen);
+
/* transaction related */
typedef int (*pdo_dbh_txn_func)(pdo_dbh_t *dbh TSRMLS_DC);
@@ -311,6 +314,7 @@ struct pdo_dbh_methods {
pdo_dbh_get_driver_methods_func get_driver_methods;
pdo_dbh_request_shutdown persistent_shutdown;
pdo_dbh_txn_func in_transaction;
+ pdo_dbh_quote_name_func name_quoter;
};
/* }}} */
View
23 ext/pdo_dblib/dblib_driver.c
@@ -166,6 +166,26 @@ static int dblib_handle_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquote
return 1;
}
+/* {{{ dblib_handle_name_quoter */
+static int dblib_handle_name_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquotedlen, char **quoted, int *quotedlen TSRMLS_DC)
+{
+ int i;
+ int j = 0;
+ *quoted = safe_emalloc(2, unquotedlen, 3);
+ (*quoted)[j++] = '[';
+ for (i = 0; i < unquotedlen; i++) {
+ (*quoted)[j++] = unquoted[i];
+ if (unquoted[i] == ']') {
+ (*quoted)[j++] = ']';
+ }
+ }
+ (*quoted)[j++] = ']';
+ (*quoted)[j] = '\0';
+ *quotedlen = j;
+ return 1;
+}
+/* }}} */
+
static int pdo_dblib_transaction_cmd(const char *cmd, pdo_dbh_t *dbh TSRMLS_DC)
{
pdo_dblib_db_handle *H = (pdo_dblib_db_handle *)dbh->driver_data;
@@ -256,7 +276,8 @@ static struct pdo_dbh_methods dblib_methods = {
NULL, /* check liveness */
NULL, /* get driver methods */
NULL, /* request shutdown */
- NULL /* in transaction */
+ NULL, /* in_transaction */
+ dblib_handle_name_quoter,
};
static int pdo_dblib_handle_factory(pdo_dbh_t *dbh, zval *driver_options TSRMLS_DC)
View
26 ext/pdo_firebird/firebird_driver.c
@@ -313,6 +313,26 @@ static int firebird_handle_quoter(pdo_dbh_t *dbh, const char *unquoted, int unqu
}
/* }}} */
+/* {{{ firebird_handle_name_quoter */
+static int firebird_handle_name_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquotedlen, char **quoted, int *quotedlen TSRMLS_DC)
+{
+ int i;
+ int j = 0;
+ *quoted = safe_emalloc(2, unquotedlen, 3);
+ (*quoted)[j++] = '"';
+ for (i = 0; i < unquotedlen; i++) {
+ (*quoted)[j++] = unquoted[i];
+ if (unquoted[i] == '"') {
+ (*quoted)[j++] = '"';
+ }
+ }
+ (*quoted)[j++] = '"';
+ (*quoted)[j] = '\0';
+ *quotedlen = j;
+ return 1;
+}
+/* }}} */
+
/* called by PDO to start a transaction */
static int firebird_handle_begin(pdo_dbh_t *dbh TSRMLS_DC) /* {{{ */
{
@@ -639,7 +659,11 @@ static struct pdo_dbh_methods firebird_methods = { /* {{{ */
NULL, /* last_id not supported */
pdo_firebird_fetch_error_func,
firebird_handle_get_attribute,
- NULL /* check_liveness */
+ NULL, /* check liveness */
+ NULL, /* get driver methods */
+ NULL, /* request shutdown */
+ NULL, /* in_transaction */
+ firebird_handle_name_quoter,
};
/* }}} */
View
33 ext/pdo_mysql/mysql_driver.c
@@ -314,10 +314,35 @@ static int mysql_handle_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquote
}
/* }}} */
+/* {{{ mysql_handle_name_quoter */
+static int mysql_handle_name_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquotedlen, char **quoted, int *quotedlen TSRMLS_DC)
+{
+ pdo_mysql_db_handle *H = (pdo_mysql_db_handle *)dbh->driver_data;
+ int i;
+ int j = 0;
+ PDO_DBG_ENTER("mysql_handle_name_quoter");
+ PDO_DBG_INF_FMT("dbh=%p", dbh);
+ PDO_DBG_INF_FMT("unquoted=%.*s", unquotedlen, unquoted);
+ *quoted = safe_emalloc(2, unquotedlen, 3);
+ (*quoted)[j++] = '`';
+ for (i = 0; i < unquotedlen; i++) {
+ (*quoted)[j++] = unquoted[i];
+ if (unquoted[i] == '`') {
+ (*quoted)[j++] = '`';
+ }
+ }
+ (*quoted)[j++] = '`';
+ (*quoted)[j] = '\0';
+ *quotedlen = j;
+ PDO_DBG_INF_FMT("quoted=%.*s", *quotedlen, *quoted);
+ PDO_DBG_RETURN(1);
+}
+/* }}} */
+
/* {{{ mysql_handle_begin */
static int mysql_handle_begin(pdo_dbh_t *dbh TSRMLS_DC)
{
- PDO_DBG_ENTER("mysql_handle_quoter");
+ PDO_DBG_ENTER("mysql_handle_begin");
PDO_DBG_INF_FMT("dbh=%p", dbh);
PDO_DBG_RETURN(0 <= mysql_handle_doer(dbh, ZEND_STRL("START TRANSACTION") TSRMLS_CC));
}
@@ -522,7 +547,11 @@ static struct pdo_dbh_methods mysql_methods = {
pdo_mysql_last_insert_id,
pdo_mysql_fetch_error_func,
pdo_mysql_get_attribute,
- pdo_mysql_check_liveness
+ pdo_mysql_check_liveness,
+ NULL, /* get_driver_methods */
+ NULL, /* persistent_shutdown */
+ NULL, /* in_transaction */
+ mysql_handle_name_quoter,
};
/* }}} */
View
25 ext/pdo_oci/oci_driver.c
@@ -403,6 +403,26 @@ static int oci_handle_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquotedl
}
/* }}} */
+/* {{{ oci_handle_name_quoter */
+static int oci_handle_name_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquotedlen, char **quoted, int *quotedlen TSRMLS_DC)
+{
+ int i;
+ int j = 0;
+ *quoted = safe_emalloc(2, unquotedlen, 3);
+ (*quoted)[j++] = '"';
+ for (i = 0; i < unquotedlen; i++) {
+ (*quoted)[j++] = unquoted[i];
+ if (unquoted[i] == '"') {
+ (*quoted)[j++] = '"';
+ }
+ }
+ (*quoted)[j++] = '"';
+ (*quoted)[j] = '\0';
+ *quotedlen = j;
+ return 1;
+}
+/* }}} */
+
static int oci_handle_begin(pdo_dbh_t *dbh TSRMLS_DC) /* {{{ */
{
/* with Oracle, there is nothing special to be done */
@@ -581,7 +601,10 @@ static struct pdo_dbh_methods oci_methods = {
pdo_oci_fetch_error_func,
oci_handle_get_attribute,
pdo_oci_check_liveness, /* check_liveness */
- NULL /* get_driver_methods */
+ NULL, /* get_driver_methods */
+ NULL, /* persistent_shutdown */
+ NULL, /* in_transaction */
+ oci_handle_name_quoter,
};
static int pdo_oci_handle_factory(pdo_dbh_t *dbh, zval *driver_options TSRMLS_DC) /* {{{ */
View
23 ext/pdo_pgsql/pgsql_driver.c
@@ -342,6 +342,26 @@ static int pgsql_handle_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquote
return 1;
}
+/* {{{ pgsql_handle_name_quoter */
+static int pgsql_handle_name_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquotedlen, char **quoted, int *quotedlen TSRMLS_DC)
+{
+ int i;
+ int j = 0;
+ *quoted = safe_emalloc(2, unquotedlen, 3);
+ (*quoted)[j++] = '"';
+ for (i = 0; i < unquotedlen; i++) {
+ (*quoted)[j++] = unquoted[i];
+ if (unquoted[i] == '"') {
+ (*quoted)[j++] = '"';
+ }
+ }
+ (*quoted)[j++] = '"';
+ (*quoted)[j] = '\0';
+ *quotedlen = j;
+ return 1;
+}
+/* }}} */
+
static char *pdo_pgsql_last_insert_id(pdo_dbh_t *dbh, const char *name, unsigned int *len TSRMLS_DC)
{
pdo_pgsql_db_handle *H = (pdo_pgsql_db_handle *)dbh->driver_data;
@@ -1030,8 +1050,9 @@ static struct pdo_dbh_methods pgsql_methods = {
pdo_pgsql_get_attribute,
pdo_pgsql_check_liveness, /* check_liveness */
pdo_pgsql_get_driver_methods, /* get_driver_methods */
- NULL,
+ NULL, /* persistent_shutdown */
pgsql_handle_in_transaction,
+ pgsql_handle_name_quoter,
};
static int pdo_pgsql_handle_factory(pdo_dbh_t *dbh, zval *driver_options TSRMLS_DC) /* {{{ */
View
24 ext/pdo_sqlite/sqlite_driver.c
@@ -238,6 +238,26 @@ static int sqlite_handle_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquot
return 1;
}
+/* {{{ sqlite_handle_name_quoter */
+static int sqlite_handle_name_quoter(pdo_dbh_t *dbh, const char *unquoted, int unquotedlen, char **quoted, int *quotedlen TSRMLS_DC)
+{
+ int i;
+ int j = 0;
+ *quoted = safe_emalloc(2, unquotedlen, 3);
+ (*quoted)[j++] = '"';
+ for (i = 0; i < unquotedlen; i++) {
+ (*quoted)[j++] = unquoted[i];
+ if (unquoted[i] == '"') {
+ (*quoted)[j++] = '"';
+ }
+ }
+ (*quoted)[j++] = '"';
+ (*quoted)[j] = '\0';
+ *quotedlen = j;
+ return 1;
+}
+/* }}} */
+
static int sqlite_handle_begin(pdo_dbh_t *dbh TSRMLS_DC)
{
pdo_sqlite_db_handle *H = (pdo_sqlite_db_handle *)dbh->driver_data;
@@ -755,7 +775,9 @@ static struct pdo_dbh_methods sqlite_methods = {
pdo_sqlite_get_attribute,
NULL, /* check_liveness: not needed */
get_driver_methods,
- pdo_sqlite_request_shutdown
+ pdo_sqlite_request_shutdown,
+ NULL, /* in_transaction */
+ sqlite_handle_name_quoter,
};
static char *make_filename_safe(const char *filename TSRMLS_DC)
View
20 ext/pdo_sqlite/tests/pdo_sqlite_quote_name.phpt
@@ -0,0 +1,20 @@
+--TEST--
+PDO SQLite quote name
+--SKIPIF--
+<?php
+if (!extension_loaded('pdo_sqlite')) print 'skip not loaded';
+?>
+--FILE--
+<?php
+$pdo = new PDO("sqlite::memory:");
+
+echo $pdo->quoteName('id') . "\n";
+echo $pdo->quoteName('order') . "\n";
+echo $pdo->quoteName('') . "\n";
+echo $pdo->quoteName('x"y') . "\n";
+?>
+--EXPECT--
+"id"
+"order"
+""
+"x""y"
Please sign in to comment.
Something went wrong with that request. Please try again.