summaryrefslogtreecommitdiff
path: root/ext/pgsql
diff options
context:
space:
mode:
Diffstat (limited to 'ext/pgsql')
-rw-r--r--ext/pgsql/config.m43
-rw-r--r--ext/pgsql/config.w324
-rw-r--r--ext/pgsql/pgsql.c80
-rw-r--r--ext/pgsql/php_pgsql.h4
-rw-r--r--ext/pgsql/tests/02connection.phpt2
-rw-r--r--ext/pgsql/tests/80_bug39971.phpt30
6 files changed, 81 insertions, 42 deletions
diff --git a/ext/pgsql/config.m4 b/ext/pgsql/config.m4
index 88d0faff1..d62ef296a 100644
--- a/ext/pgsql/config.m4
+++ b/ext/pgsql/config.m4
@@ -1,5 +1,5 @@
dnl
-dnl $Id: config.m4,v 1.46.2.1.2.3 2006/10/06 21:45:10 iliaa Exp $
+dnl $Id: config.m4,v 1.46.2.1.2.4 2007/02/18 17:05:53 iliaa Exp $
dnl
AC_DEFUN([PHP_PGSQL_CHECK_FUNCTIONS],[
@@ -89,6 +89,7 @@ if test "$PHP_PGSQL" != "no"; then
AC_CHECK_LIB(pq, PQputCopyData,AC_DEFINE(HAVE_PQPUTCOPYDATA,1,[PostgreSQL 7.4 or later]))
AC_CHECK_LIB(pq, PQputCopyEnd,AC_DEFINE(HAVE_PQPUTCOPYEND,1,[PostgreSQL 7.4 or later]))
AC_CHECK_LIB(pq, PQgetCopyData,AC_DEFINE(HAVE_PQGETCOPYDATA,1,[PostgreSQL 7.4 or later]))
+ AC_CHECK_LIB(pq, PQfreemem,AC_DEFINE(HAVE_PQFREEMEM,1,[PostgreSQL 7.4 or later]))
AC_CHECK_LIB(pq, PQsetErrorVerbosity,AC_DEFINE(HAVE_PQSETERRORVERBOSITY,1,[PostgreSQL 7.4 or later]))
AC_CHECK_LIB(pq, PQftable,AC_DEFINE(HAVE_PQFTABLE,1,[PostgreSQL 7.4 or later]))
AC_CHECK_LIB(pq, PQescapeStringConn, AC_DEFINE(HAVE_PQESCAPE_CONN,1,[PostgreSQL 8.1.4 or later]))
diff --git a/ext/pgsql/config.w32 b/ext/pgsql/config.w32
index 414bfbd97..87ef7c99c 100644
--- a/ext/pgsql/config.w32
+++ b/ext/pgsql/config.w32
@@ -1,4 +1,4 @@
-// $Id: config.w32,v 1.7.4.3 2006/10/11 11:00:02 edink Exp $
+// $Id: config.w32,v 1.7.4.5 2007/02/19 17:26:15 edink Exp $
// vim:ft=javascript
ARG_WITH("pgsql", "PostgreSQL support", "no");
@@ -8,7 +8,7 @@ if (PHP_PGSQL != "no") {
CHECK_HEADER_ADD_INCLUDE("libpq-fe.h", "CFLAGS_PGSQL", PHP_PGSQL + "\\include;" + PHP_PHP_BUILD + "\\include\\pgsql;" + PHP_PGSQL)) {
EXTENSION("pgsql", "pgsql.c");
AC_DEFINE('HAVE_PGSQL', 1, 'Have PostgreSQL library');
- ADD_FLAG("CFLAGS_PGSQL", "/D HAVE_PG_CONFIG_H /D PGSQL_EXPORTS /D HAVE_PQSETNONBLOCKING /D HAVE_PQCMDTUPLES /D HAVE_PQCLIENTENCODING /D HAVE_PQESCAPE /D HAVE_PQPARAMETERSTATUS /D HAVE_PGTRANSACTIONSTATUS /D HAVE_PQEXECPARAMS /D HAVE_PQPREPARE /D HAVE_PQEXECPREPARED /D HAVE_PQRESULTERRORFIELD /D HAVE_PQSENDQUERYPARAMS /D HAVE_PQSENDPREPARE /D HAVE_PQSENDQUERYPREPARED /D HAVE_PQPUTCOPYDATA /D HAVE_PQPUTCOPYEND /D HAVE_PQGETCOPYDATA /D HAVE_PQSETERRORVERBOSITY /D HAVE_PQUNESCAPEBYTEA /D HAVE_PQFTABLE /D HAVE_PQESCAPE_CONN /D HAVE_PQESCAPE_BYTEA_CONN");
+ ADD_FLAG("CFLAGS_PGSQL", "/D HAVE_PG_CONFIG_H /D PGSQL_EXPORTS /D HAVE_PQSETNONBLOCKING /D HAVE_PQCMDTUPLES /D HAVE_PQCLIENTENCODING /D HAVE_PQESCAPE /D HAVE_PQPARAMETERSTATUS /D HAVE_PGTRANSACTIONSTATUS /D HAVE_PQEXECPARAMS /D HAVE_PQPREPARE /D HAVE_PQEXECPREPARED /D HAVE_PQRESULTERRORFIELD /D HAVE_PQSENDQUERYPARAMS /D HAVE_PQSENDPREPARE /D HAVE_PQSENDQUERYPREPARED /D HAVE_PQPUTCOPYDATA /D HAVE_PQPUTCOPYEND /D HAVE_PQGETCOPYDATA /D HAVE_PQSETERRORVERBOSITY /D HAVE_PQUNESCAPEBYTEA /D HAVE_PQFTABLE /D HAVE_PQESCAPE_CONN /D HAVE_PQESCAPE_BYTEA_CONN /D HAVE_PQFREEMEM /D HAVE_PGSQL_WITH_MULTIBYTE_SUPPORT");
} else {
WARNING("pgsql not enabled; libraries and headers not found");
}
diff --git a/ext/pgsql/pgsql.c b/ext/pgsql/pgsql.c
index 7439d7f3d..adf49345a 100644
--- a/ext/pgsql/pgsql.c
+++ b/ext/pgsql/pgsql.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2006 The PHP Group |
+ | Copyright (c) 1997-2007 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -20,7 +20,7 @@
+----------------------------------------------------------------------+
*/
-/* $Id: pgsql.c,v 1.331.2.13.2.9 2006/10/06 21:45:10 iliaa Exp $ */
+/* $Id: pgsql.c,v 1.331.2.13.2.20 2007/02/24 02:17:25 helly Exp $ */
#include <stdlib.h>
@@ -599,9 +599,9 @@ PHP_MINFO_FUNCTION(pgsql)
php_info_print_table_row(2, "SSL support", "disabled");
#endif
#endif /* HAVE_PG_CONFIG_H */
- sprintf(buf, "%ld", PGG(num_persistent));
+ snprintf(buf, sizeof(buf), "%ld", PGG(num_persistent));
php_info_print_table_row(2, "Active Persistent Links", buf);
- sprintf(buf, "%ld", PGG(num_links));
+ snprintf(buf, sizeof(buf), "%ld", PGG(num_links));
php_info_print_table_row(2, "Active Links", buf);
php_info_print_table_end();
@@ -629,6 +629,16 @@ static void php_pgsql_do_connect(INTERNAL_FUNCTION_PARAMETERS, int persistent)
smart_str_appends(&str, "pgsql");
for (i = 0; i < ZEND_NUM_ARGS(); i++) {
+ /* make sure that the PGSQL_CONNECT_FORCE_NEW bit is not part of the hash so that subsequent connections
+ * can re-use this connection. Bug #39979
+ */
+ if (i == 1 && ZEND_NUM_ARGS() == 2 && Z_TYPE_PP(args[i]) == IS_LONG) {
+ if (Z_LVAL_PP(args[1]) == PGSQL_CONNECT_FORCE_NEW) {
+ continue;
+ } else if (Z_LVAL_PP(args[1]) & PGSQL_CONNECT_FORCE_NEW) {
+ smart_str_append_long(&str, Z_LVAL_PP(args[1]) ^ PGSQL_CONNECT_FORCE_NEW);
+ }
+ }
convert_to_string_ex(args[i]);
smart_str_appendc(&str, '_');
smart_str_appendl(&str, Z_STRVAL_PP(args[i]), Z_STRLEN_PP(args[i]));
@@ -1472,6 +1482,7 @@ PHP_FUNCTION(pg_execute)
php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Found results on this connection. Use pg_get_result() to get these results first");
}
+ SEPARATE_ZVAL(pv_param_arr);
zend_hash_internal_pointer_reset(Z_ARRVAL_PP(pv_param_arr));
num_params = zend_hash_num_elements(Z_ARRVAL_PP(pv_param_arr));
if (num_params > 0) {
@@ -1486,7 +1497,8 @@ PHP_FUNCTION(pg_execute)
}
otype = (*tmp)->type;
- convert_to_string(*tmp);
+ SEPARATE_ZVAL(tmp);
+ convert_to_string_ex(tmp);
if (Z_TYPE_PP(tmp) != IS_STRING) {
php_error_docref(NULL TSRMLS_CC, E_WARNING,"Error converting parameter");
_php_pgsql_free_params(params, num_params);
@@ -1495,8 +1507,7 @@ PHP_FUNCTION(pg_execute)
if (otype == IS_NULL) {
params[i] = NULL;
- }
- else {
+ } else {
params[i] = Z_STRVAL_PP(tmp);
}
@@ -2101,7 +2112,7 @@ static void php_pgsql_fetch_hash(INTERNAL_FUNCTION_PARAMETERS, long result_type,
Bucket *p;
fci.param_count = 0;
- fci.params = emalloc(sizeof(zval*) * ht->nNumOfElements);
+ fci.params = safe_emalloc(sizeof(zval*), ht->nNumOfElements, 0);
p = ht->pListHead;
while (p != NULL) {
fci.params[fci.param_count++] = (zval**)p->pData;
@@ -3292,7 +3303,6 @@ PHP_FUNCTION(pg_copy_to)
char *table_name, *pg_delim = NULL, *pg_null_as = NULL;
int table_name_len, pg_delim_len, pg_null_as_len;
char *query;
- char *query_template = "COPY \"\" TO STDOUT DELIMITERS ':' WITH NULL AS ''";
int id = -1;
PGconn *pgsql;
PGresult *pgsql_result;
@@ -3320,9 +3330,7 @@ PHP_FUNCTION(pg_copy_to)
pg_null_as = safe_estrdup("\\\\N");
}
- query = (char *)emalloc(strlen(query_template) + strlen(table_name) + strlen(pg_null_as) + 1);
- sprintf(query, "COPY \"%s\" TO STDOUT DELIMITERS '%c' WITH NULL AS '%s'",
- table_name, *pg_delim, pg_null_as);
+ spprintf(&query, 0, "COPY \"%s\" TO STDOUT DELIMITERS '%c' WITH NULL AS '%s'", table_name, *pg_delim, pg_null_as);
while ((pgsql_result = PQgetResult(pgsql))) {
PQclear(pgsql_result);
@@ -3357,7 +3365,7 @@ PHP_FUNCTION(pg_copy_to)
break;
default:
add_next_index_string(return_value, csv, 1);
- free(csv);
+ PQfreemem(csv);
break;
}
}
@@ -3430,7 +3438,6 @@ PHP_FUNCTION(pg_copy_from)
int table_name_len, pg_delim_len, pg_null_as_len;
int pg_null_as_free = 0;
char *query;
- char *query_template = "COPY \"\" FROM STDIN DELIMITERS ':' WITH NULL AS ''";
HashPosition pos;
int id = -1;
PGconn *pgsql;
@@ -3453,9 +3460,7 @@ PHP_FUNCTION(pg_copy_from)
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
- query = (char *)emalloc(strlen(query_template) + strlen(table_name) + strlen(pg_null_as) + 1);
- sprintf(query, "COPY \"%s\" FROM STDIN DELIMITERS '%c' WITH NULL AS '%s'",
- table_name, *pg_delim, pg_null_as);
+ spprintf(&query, 0, "COPY \"%s\" FROM STDIN DELIMITERS '%c' WITH NULL AS '%s'", table_name, *pg_delim, pg_null_as);
while ((pgsql_result = PQgetResult(pgsql))) {
PQclear(pgsql_result);
}
@@ -3481,10 +3486,11 @@ PHP_FUNCTION(pg_copy_from)
#if HAVE_PQPUTCOPYDATA
while (zend_hash_get_current_data_ex(Z_ARRVAL_P(pg_rows), (void **) &tmp, &pos) == SUCCESS) {
convert_to_string_ex(tmp);
- query = (char *)emalloc(Z_STRLEN_PP(tmp) +2);
- strcpy(query, Z_STRVAL_PP(tmp));
- if(*(query+Z_STRLEN_PP(tmp)-1) != '\n')
- strcat(query, "\n");
+ query = (char *)emalloc(Z_STRLEN_PP(tmp) + 2);
+ strlcpy(query, Z_STRVAL_PP(tmp), Z_STRLEN_PP(tmp) + 2);
+ if(Z_STRLEN_PP(tmp) > 0 && *(query + Z_STRLEN_PP(tmp) - 1) != '\n') {
+ strlcat(query, "\n", Z_STRLEN_PP(tmp) + 2);
+ }
if (PQputCopyData(pgsql, query, strlen(query)) != 1) {
efree(query);
PHP_PQ_ERROR("copy failed: %s", pgsql);
@@ -3500,10 +3506,11 @@ PHP_FUNCTION(pg_copy_from)
#else
while (zend_hash_get_current_data_ex(Z_ARRVAL_P(pg_rows), (void **) &tmp, &pos) == SUCCESS) {
convert_to_string_ex(tmp);
- query = (char *)emalloc(Z_STRLEN_PP(tmp) +2);
- strcpy(query, Z_STRVAL_PP(tmp));
- if(*(query+Z_STRLEN_PP(tmp)-1) != '\n')
- strcat(query, "\n");
+ query = (char *)emalloc(Z_STRLEN_PP(tmp) + 2);
+ strlcpy(query, Z_STRVAL_PP(tmp), Z_STRLEN_PP(tmp) + 2);
+ if(Z_STRLEN_PP(tmp) > 0 && *(query + Z_STRLEN_PP(tmp) - 1) != '\n') {
+ strlcat(query, "\n", Z_STRLEN_PP(tmp) + 2);
+ }
if (PQputline(pgsql, query)==EOF) {
efree(query);
PHP_PQ_ERROR("copy failed: %s", pgsql);
@@ -3609,7 +3616,7 @@ PHP_FUNCTION(pg_escape_bytea)
to = (char *)PQescapeBytea((unsigned char*)from, from_len, &to_len);
RETVAL_STRINGL(to, to_len-1, 1); /* to_len includes addtional '\0' */
- free(to);
+ PQfreemem(to);
}
/* }}} */
@@ -3734,7 +3741,7 @@ PHP_FUNCTION(pg_unescape_bytea)
#if HAVE_PQUNESCAPEBYTEA
tmp = (char *)PQunescapeBytea((unsigned char*)from, &to_len);
to = estrndup(tmp, to_len);
- free(tmp);
+ PQfreemem(tmp);
#else
to = (char *)php_pgsql_unescape_bytea((unsigned char*)from, &to_len);
#endif
@@ -4347,6 +4354,7 @@ PHP_FUNCTION(pg_get_notify)
add_assoc_string(return_value, "message", pgsql_notify->relname, 1);
add_assoc_long(return_value, "pid", pgsql_notify->be_pid);
}
+ PQfreemem(pgsql_notify);
}
/* }}} */
@@ -4966,14 +4974,14 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
switch(Z_TYPE_PP(val)) {
case IS_STRING:
if (Z_STRLEN_PP(val) == 0) {
- ZVAL_STRING(new_val, "NULL", 1);
- }
- else {
+ ZVAL_STRINGL(new_val, "NULL", sizeof("NULL")-1, 1);
+ } else if (!strcasecmp(Z_STRVAL_PP(val), "now()")) {
+ ZVAL_STRINGL(new_val, "NOW()", sizeof("NOW()")-1, 1);
+ } else {
/* FIXME: better regex must be used */
if (php_pgsql_convert_match(Z_STRVAL_PP(val), "^([0-9]{4}[/-][0-9]{1,2}[/-][0-9]{1,2})([ \\t]+(([0-9]{1,2}:[0-9]{1,2}){1}(:[0-9]{1,2}){0,1}(\\.[0-9]+){0,1}([ \\t]*([+-][0-9]{1,2}(:[0-9]{1,2}){0,1}|[a-zA-Z]{1,5})){0,1})){0,1}$", 1 TSRMLS_CC) == FAILURE) {
err = 1;
- }
- else {
+ } else {
ZVAL_STRING(new_val, Z_STRVAL_PP(val), 1);
php_pgsql_add_quotes(new_val, 1 TSRMLS_CC);
}
@@ -4981,7 +4989,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
break;
case IS_NULL:
- ZVAL_STRING(new_val, "NULL", 1);
+ ZVAL_STRINGL(new_val, "NULL", sizeof("NULL")-1, 1);
break;
default:
@@ -5152,7 +5160,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
Z_STRLEN_P(new_val) = to_len-1; /* PQescapeBytea's to_len includes additional '\0' */
Z_STRVAL_P(new_val) = emalloc(to_len);
memcpy(Z_STRVAL_P(new_val), tmp, to_len);
- free(tmp);
+ PQfreemem(tmp);
php_pgsql_add_quotes(new_val, 1 TSRMLS_CC);
}
@@ -5381,7 +5389,7 @@ PHP_PGSQL_API int php_pgsql_insert(PGconn *pg_link, const char *table, zval *var
smart_str_append_long(&querystr, Z_LVAL_PP(val));
break;
case IS_DOUBLE:
- smart_str_appendl(&querystr, buf, snprintf(buf, sizeof(buf), "%f", Z_DVAL_PP(val)));
+ smart_str_appendl(&querystr, buf, snprintf(buf, sizeof(buf), "%F", Z_DVAL_PP(val)));
break;
default:
/* should not happen */
@@ -5483,7 +5491,7 @@ static inline int build_assignment_string(smart_str *querystr, HashTable *ht, co
smart_str_append_long(querystr, Z_LVAL_PP(val));
break;
case IS_DOUBLE:
- smart_str_appendl(querystr, buf, sprintf(buf, "%f", Z_DVAL_PP(val)));
+ smart_str_appendl(querystr, buf, MIN(snprintf(buf, sizeof(buf), "%F", Z_DVAL_PP(val)), sizeof(buf)-1));
break;
default:
/* should not happen */
diff --git a/ext/pgsql/php_pgsql.h b/ext/pgsql/php_pgsql.h
index 0b31b3733..128f762f4 100644
--- a/ext/pgsql/php_pgsql.h
+++ b/ext/pgsql/php_pgsql.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2006 The PHP Group |
+ | Copyright (c) 1997-2007 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -17,7 +17,7 @@
+----------------------------------------------------------------------+
*/
-/* $Id: php_pgsql.h,v 1.73.2.1.2.1 2006/05/07 00:28:32 edink Exp $ */
+/* $Id: php_pgsql.h,v 1.73.2.1.2.2 2007/01/01 09:36:05 sebastian Exp $ */
#ifndef PHP_PGSQL_H
#define PHP_PGSQL_H
diff --git a/ext/pgsql/tests/02connection.phpt b/ext/pgsql/tests/02connection.phpt
index 6288d0e17..234427ba1 100644
--- a/ext/pgsql/tests/02connection.phpt
+++ b/ext/pgsql/tests/02connection.phpt
@@ -29,7 +29,7 @@ if (function_exists('pg_transaction_status')) {
echo "pg_transaction_status() error\n";
}
}
-if (!pg_host($db))
+if (false === pg_host($db))
{
echo "pg_host() error\n";
}
diff --git a/ext/pgsql/tests/80_bug39971.phpt b/ext/pgsql/tests/80_bug39971.phpt
new file mode 100644
index 000000000..45d26319d
--- /dev/null
+++ b/ext/pgsql/tests/80_bug39971.phpt
@@ -0,0 +1,30 @@
+--TEST--
+Bug #39971 (pg_insert/pg_update do not allow now() to be used for timestamp fields)
+--SKIPIF--
+<?php
+require_once('skipif.inc');
+?>
+--FILE--
+<?php
+
+require_once('config.inc');
+
+$dbh = @pg_connect($conn_str);
+if (!$dbh) {
+ die ("Could not connect to the server");
+}
+
+pg_query("CREATE TABLE php_test (id SERIAL, tm timestamp NOT NULL)");
+
+$values = array('tm' => 'now()');
+pg_insert($dbh, 'php_test', $values);
+
+$ids = array('id' => 1);
+pg_update($dbh, 'php_test', $values, $ids);
+
+pg_query($dbh, "DROP TABLE php_test");
+pg_close($dbh);
+?>
+===DONE===
+--EXPECT--
+===DONE===