From 182c02c5e859abbaf65d2e24fec90ebfa5f1c33b Mon Sep 17 00:00:00 2001 From: Marc Delisle Date: Sat, 21 Nov 2009 13:22:08 +0000 Subject: [PATCH] bug #2893221 [core] Statement may not be safe to log in statement format --- ChangeLog | 1 + libraries/common.lib.php | 7 +++-- libraries/display_tbl.lib.php | 43 +++++++++++++++++------------ libraries/display_tbl_links.lib.php | 4 +-- libraries/export/sql.php | 4 ++- tbl_change.php | 16 +++++++---- tbl_replace.php | 10 +++---- 7 files changed, 52 insertions(+), 33 deletions(-) diff --git a/ChangeLog b/ChangeLog index 4648c5c64..375c26f18 100644 --- a/ChangeLog +++ b/ChangeLog @@ -58,6 +58,7 @@ $HeadURL: https://phpmyadmin.svn.sourceforge.net/svnroot/phpmyadmin/trunk/phpMyA - bug #2823599 [edit] UUID Primary Key wrongly updated - bug #2895894 [structure] Empty default value not set properly - bug #2897536 [parser] Copying table with bit field with default +- bug #2893221 [core] Statement may not be safe to log in statement format 3.2.3.0 (2009-10-30) - patch #2856664 [export] Date, time, and datetime column types now export correctly to diff --git a/libraries/common.lib.php b/libraries/common.lib.php index 94d7d8240..3f016d548 100644 --- a/libraries/common.lib.php +++ b/libraries/common.lib.php @@ -1925,7 +1925,7 @@ function PMA_checkParameters($params, $die = true, $request = true) * * @access public * @author Michal Cihar (michal@cihar.com) and others... - * @return string calculated condition + * @return string the calculated condition and whether condition is unique */ function PMA_getUniqueCondition($handle, $fields_cnt, $fields_meta, $row, $force_unique=false) { @@ -2023,15 +2023,18 @@ function PMA_getUniqueCondition($handle, $fields_cnt, $fields_meta, $row, $force // Correction University of Virginia 19991216: // prefer primary or unique keys for condition, // but use conjunction of all values if no primary key + $clause_is_unique = true; if ($primary_key) { $preferred_condition = $primary_key; } elseif ($unique_key) { $preferred_condition = $unique_key; } elseif (! $force_unique) { $preferred_condition = $nonprimary_condition; + $clause_is_unique = false; } - return trim(preg_replace('|\s?AND$|', '', $preferred_condition)); + $where_clause = trim(preg_replace('|\s?AND$|', '', $preferred_condition)); + return(array($where_clause, $clause_is_unique)); } // end function /** diff --git a/libraries/display_tbl.lib.php b/libraries/display_tbl.lib.php index d190b6e8b..7b5740d62 100644 --- a/libraries/display_tbl.lib.php +++ b/libraries/display_tbl.lib.php @@ -442,7 +442,7 @@ onsubmit="return (checkFormElementInRange(this, 'session_max_rows', ' builds the - // "primary" key to use in links + // WHERE clause to use in links (a unique key if possible) /** - * @todo $unique_condition could be empty, for example a table + * @todo $where_clause could be empty, for example a table * with only one field and it's a BLOB; in this case, * avoid to display the delete and edit links */ - $unique_condition = PMA_getUniqueCondition($dt_result, $fields_cnt, $fields_meta, $row); - $unique_condition_html = urlencode($unique_condition); + list($where_clause, $clause_is_unique) = PMA_getUniqueCondition($dt_result, $fields_cnt, $fields_meta, $row); + $where_clause_html = urlencode($where_clause); // 1.2 Defines the URLs for the modify/delete link(s) @@ -1099,11 +1099,12 @@ function PMA_displayTableBody(&$dt_result, &$is_display, $map, $analyzed_sql) { // 1.2.1 Modify link(s) if ($is_display['edit_lnk'] == 'ur') { // update row case $_url_params = array( - 'db' => $db, - 'table' => $table, - 'primary_key' => $unique_condition, - 'sql_query' => $url_sql_query, - 'goto' => 'sql.php', + 'db' => $db, + 'table' => $table, + 'primary_key' => $where_clause, + 'clause_is_unique' => $clause_is_unique, + 'sql_query' => $url_sql_query, + 'goto' => 'sql.php', ); $edit_url = 'tbl_change.php' . PMA_generate_common_url($_url_params); @@ -1141,7 +1142,7 @@ function PMA_displayTableBody(&$dt_result, &$is_display, $map, $analyzed_sql) { $lnk_goto = 'sql.php' . PMA_generate_common_url($_url_params, 'text'); $del_query = 'DELETE FROM ' . PMA_backquote($db) . '.' . PMA_backquote($table) - . ' WHERE ' . $unique_condition . ' LIMIT 1'; + . ' WHERE ' . $where_clause . ($clause_is_unique ? '' : ' LIMIT 1'); $_url_params = array( 'db' => $db, @@ -1153,8 +1154,8 @@ function PMA_displayTableBody(&$dt_result, &$is_display, $map, $analyzed_sql) { $del_url = 'sql.php' . PMA_generate_common_url($_url_params); $js_conf = 'DELETE FROM ' . PMA_jsFormat($db) . '.' . PMA_jsFormat($table) - . ' WHERE ' . PMA_jsFormat($unique_condition, false) - . ' LIMIT 1'; + . ' WHERE ' . PMA_jsFormat($where_clause, false) + . ($clause_is_unique ? '' : ' LIMIT 1'); $del_str = PMA_getIcon('b_drop.png', $GLOBALS['strDelete'], true); } elseif ($is_display['del_lnk'] == 'kp') { // kill process case @@ -1238,7 +1239,7 @@ function PMA_displayTableBody(&$dt_result, &$is_display, $map, $analyzed_sql) { $_url_params = array( 'db' => $db, 'table' => $table, - 'primary_key' => $unique_condition, + 'primary_key' => $where_clause, 'transform_key' => $meta->name, ); @@ -1441,7 +1442,7 @@ function PMA_displayTableBody(&$dt_result, &$is_display, $map, $analyzed_sql) { if (!empty($del_url) && $is_display['del_lnk'] != 'kp') { $vertical_display['row_delete'][$row_no] .= ' ' . "\n" - . ' ' . "\n" . ' ' . "\n"; @@ -1470,7 +1471,9 @@ function PMA_displayTableBody(&$dt_result, &$is_display, $map, $analyzed_sql) { $row_no++; } // end while - return true; + // this is needed by PMA_displayTable() to generate the proper param + // in the multi-edit and multi-delete form + return $clause_is_unique; } // end of the 'PMA_displayTableBody()' function @@ -2012,7 +2015,7 @@ function PMA_displayTable(&$dt_result, &$the_disp_mode, $analyzed_sql) PMA_displayTableHeaders($is_display, $fields_meta, $fields_cnt, $analyzed_sql, $sort_expression, $sort_expression_nodirection, $sort_direction); $url_query = ''; echo '' . "\n"; - PMA_displayTableBody($dt_result, $is_display, $map, $analyzed_sql); + $clause_is_unique = PMA_displayTableBody($dt_result, $is_display, $map, $analyzed_sql); // vertical output case if ($_SESSION['tmp_user_values']['disp_direction'] == 'vertical') { PMA_displayVerticalTable(); @@ -2023,7 +2026,7 @@ function PMA_displayTable(&$dt_result, &$the_disp_mode, $analyzed_sql) ' . "\n"; echo '' . "\n"; + + echo '' . "\n"; + echo '' . "\n"; } diff --git a/libraries/display_tbl_links.lib.php b/libraries/display_tbl_links.lib.php index 092ad55b2..8d904c0e8 100644 --- a/libraries/display_tbl_links.lib.php +++ b/libraries/display_tbl_links.lib.php @@ -21,7 +21,7 @@ if ($doWriteModifyAt == 'left') { if (!empty($del_url) && $is_display['del_lnk'] != 'kp') { echo ' ' . "\n" - . ' ' . "\n" . ' ' . "\n"; @@ -51,7 +51,7 @@ if ($doWriteModifyAt == 'left') { } if (!empty($del_url) && $is_display['del_lnk'] != 'kp') { echo ' ' . "\n" - . ' ' . "\n" . ' ' . "\n"; diff --git a/libraries/export/sql.php b/libraries/export/sql.php index 5e9c20bf5..f760193a3 100644 --- a/libraries/export/sql.php +++ b/libraries/export/sql.php @@ -1004,7 +1004,9 @@ function PMA_exportData($db, $table, $crlf, $error_url, $sql_query) $insert_line .= $field_set[$i] . ' = ' . $values[$i]; } - $insert_line .= ' WHERE ' . PMA_getUniqueCondition($result, $fields_cnt, $fields_meta, $row); + list($tmp_unique_condition, $tmp_clause_is_unique) = PMA_getUniqueCondition($result, $fields_cnt, $fields_meta, $row); + $insert_line .= ' WHERE ' . $tmp_unique_condition; + unset($tmp_unique_condition, $tmp_clause_is_unique); } else { diff --git a/tbl_change.php b/tbl_change.php index 083a6f356..1e5b3f73a 100644 --- a/tbl_change.php +++ b/tbl_change.php @@ -19,7 +19,6 @@ require_once './libraries/common.inc.php'; */ require_once './libraries/db_table_exists.lib.php'; - /** * Sets global variables. * Here it's better to use a if, instead of the '?' operator @@ -32,6 +31,9 @@ require_once './libraries/db_table_exists.lib.php'; if (isset($_REQUEST['primary_key'])) { $primary_key = $_REQUEST['primary_key']; } +if (isset($_REQUEST['clause_is_unique'])) { + $clause_is_unique = $_REQUEST['clause_is_unique']; +} if (isset($_SESSION['edit_next'])) { $primary_key = $_SESSION['edit_next']; unset($_SESSION['edit_next']); @@ -177,16 +179,17 @@ if (isset($primary_key)) { PMA_showMessage($strEmptyResultSet, $local_query); echo "\n"; require_once './libraries/footer.inc.php'; - } else { // end if (no record returned) + } else { // end if (no row returned) $meta = PMA_DBI_get_fields_meta($result[$key_id]); - if ($tmp = PMA_getUniqueCondition($result[$key_id], count($meta), $meta, $rows[$key_id], true)) { + list($unique_condition, $tmp_clause_is_unique) = PMA_getUniqueCondition($result[$key_id], count($meta), $meta, $rows[$key_id], true); + if (! empty($unique_condition)) { $found_unique_key = true; } - unset($tmp); + unset($unique_condition, $tmp_clause_is_unique); } } } else { - // no primary key given, just load first row - but what happens if tbale is empty? + // no primary key given, just load first row - but what happens if table is empty? $insert_mode = true; $result = PMA_DBI_query('SELECT * FROM ' . PMA_backquote($db) . '.' . PMA_backquote($table) . ' LIMIT 1;', null, PMA_DBI_QUERY_STORE); $rows = array_fill(0, $cfg['InsertRows'], false); @@ -233,6 +236,9 @@ if (isset($primary_keys)) { $_form_params['primary_key[' . $key_id . ']'] = trim($primary_key); } } +if (isset($clause_is_unique)) { + $_form_params['clause_is_unique'] = $clause_is_unique; +} ?> diff --git a/tbl_replace.php b/tbl_replace.php index a36ec7fce..a3602bfe8 100644 --- a/tbl_replace.php +++ b/tbl_replace.php @@ -95,11 +95,11 @@ if (isset($_REQUEST['after_insert']) $meta = PMA_DBI_get_fields_meta($res); // must find a unique condition based on unique key, // not a combination of all fields - // (the following is a real assignment) - if ($tmp = PMA_getUniqueCondition($res, count($meta), $meta, $row, true)) { - $_SESSION['edit_next'] = $tmp; + list($unique_condition, $clause_is_unique) = PMA_getUniqueCondition($res, count($meta), $meta, $row, true); + if (! empty($unique_condition)) { + $_SESSION['edit_next'] = $unique_condition; } - unset($tmp); + unset($unique_condition, $clause_is_unique); } } } @@ -298,7 +298,7 @@ foreach ($loop_array as $rowcount => $primary_key) { } else { // build update query $query[] = 'UPDATE ' . PMA_backquote($GLOBALS['db']) . '.' . PMA_backquote($GLOBALS['table']) - . ' SET ' . implode(', ', $query_values) . ' WHERE ' . $primary_key . ' LIMIT 1'; + . ' SET ' . implode(', ', $query_values) . ' WHERE ' . $primary_key . ($_REQUEST['clause_is_unique'] ? '' : ' LIMIT 1'); } }