From c3b98bed7a5d0928a10f59748d062cffc2764534 Mon Sep 17 00:00:00 2001 From: "Christoph M. Becker" Date: Tue, 11 May 2021 14:40:00 +0200 Subject: [PATCH] Fix #44643: bound parameters ignore explicit type definitions If `SQLDescribeParam()` fails for a parameter, we must not assume `SQL_LONGVARCHAR` for any param which is not `PDO_PARAM_LOB`. At least mapping `PDO_PARAM_INT` to `SQL_INTEGER` should be safe, and not introduce a BC break. --- ext/pdo_odbc/odbc_stmt.c | 13 ++++++++++--- ext/pdo_odbc/tests/bug44643.phpt | 22 ++++++++++++++++++++++ 2 files changed, 32 insertions(+), 3 deletions(-) create mode 100644 ext/pdo_odbc/tests/bug44643.phpt diff --git a/ext/pdo_odbc/odbc_stmt.c b/ext/pdo_odbc/odbc_stmt.c index 368648c36ae2f..b1307be543392 100644 --- a/ext/pdo_odbc/odbc_stmt.c +++ b/ext/pdo_odbc/odbc_stmt.c @@ -323,9 +323,16 @@ static int odbc_stmt_param_hook(pdo_stmt_t *stmt, struct pdo_bound_param_data *p if (rc != SQL_SUCCESS && rc != SQL_SUCCESS_WITH_INFO) { /* MS Access, for instance, doesn't support SQLDescribeParam, * so we need to guess */ - sqltype = PDO_PARAM_TYPE(param->param_type) == PDO_PARAM_LOB ? - SQL_LONGVARBINARY : - SQL_LONGVARCHAR; + switch (PDO_PARAM_TYPE(param->param_type)) { + case PDO_PARAM_INT: + sqltype = SQL_INTEGER; + break; + case PDO_PARAM_LOB: + sqltype = SQL_LONGVARBINARY; + break; + default: + sqltype = SQL_LONGVARCHAR; + } precision = 4000; scale = 5; nullable = 1; diff --git a/ext/pdo_odbc/tests/bug44643.phpt b/ext/pdo_odbc/tests/bug44643.phpt new file mode 100644 index 0000000000000..eb96af8ba5bd0 --- /dev/null +++ b/ext/pdo_odbc/tests/bug44643.phpt @@ -0,0 +1,22 @@ +--TEST-- +Bug #44643 (bound parameters ignore explicit type definitions) +--SKIPIF-- + +--FILE-- +prepare($sql); +$id1 = 1; +$stmt->bindParam(':id1', $id1, PDO::PARAM_INT); +$id2 = 1; +$stmt->bindParam(':id2', $id2, PDO::PARAM_INT); +var_dump($stmt->execute()); +?> +--EXPECT-- +bool(true)