diff --git a/CHANGELOG.txt b/CHANGELOG.txt
index d312a68dad..4b7cea97f8 100644
--- a/CHANGELOG.txt
+++ b/CHANGELOG.txt
@@ -1,3 +1,9 @@
+Drupal 7.102, 2024-11-20
+------------------------
+- Fixed security issues:
+ - SA-CORE-2024-005
+ - SA-CORE-2024-008
+
Drupal 7.101, 2024-06-05
-----------------------
- Various security improvements
diff --git a/includes/bootstrap.inc b/includes/bootstrap.inc
index bbbdcb01c8..3757479c98 100644
--- a/includes/bootstrap.inc
+++ b/includes/bootstrap.inc
@@ -8,7 +8,7 @@
/**
* The current system version.
*/
-define('VERSION', '7.101');
+define('VERSION', '7.102');
/**
* Core API compatibility.
@@ -457,6 +457,9 @@ abstract class DrupalCacheArray implements ArrayAccess {
if ($this->bin == 'cache_form' && !variable_get('drupal_cache_array_persist_cache_form', FALSE)) {
return;
}
+ if (!is_array($this->keysToPersist)) {
+ throw new UnexpectedValueException();
+ }
$data = array();
foreach ($this->keysToPersist as $offset => $persist) {
if ($persist) {
diff --git a/includes/database/mysql/query.inc b/includes/database/mysql/query.inc
index 3f0bcb7968..525b895d2d 100644
--- a/includes/database/mysql/query.inc
+++ b/includes/database/mysql/query.inc
@@ -63,6 +63,14 @@ class InsertQuery_mysql extends InsertQuery {
$max_placeholder = 0;
$values = array();
+ if (!is_array($this->insertValues)) {
+ if (version_compare(PHP_VERSION, '7.4', '>=')) {
+ throw new UnexpectedValueException();
+ }
+ else {
+ drupal_trigger_fatal_error('Unexpected Value');
+ }
+ }
if (count($this->insertValues)) {
foreach ($this->insertValues as $insert_values) {
$placeholders = array();
@@ -96,6 +104,14 @@ class TruncateQuery_mysql extends TruncateQuery { }
class UpdateQuery_mysql extends UpdateQuery {
public function __toString() {
if (method_exists($this->connection, 'escapeField')) {
+ if (!is_array($this->fields)) {
+ if (version_compare(PHP_VERSION, '7.4', '>=')) {
+ throw new UnexpectedValueException();
+ }
+ else {
+ drupal_trigger_fatal_error('Unexpected Value');
+ }
+ }
$escapedFields = array();
foreach ($this->fields as $field => $data) {
$field = $this->connection->escapeField($field);
diff --git a/includes/database/pgsql/query.inc b/includes/database/pgsql/query.inc
index e2d587d5b7..5731e55944 100644
--- a/includes/database/pgsql/query.inc
+++ b/includes/database/pgsql/query.inc
@@ -120,7 +120,15 @@ class InsertQuery_pgsql extends InsertQuery {
$max_placeholder = 0;
$values = array();
- if (count($this->insertValues)) {
+ if (!is_array($this->insertValues)) {
+ if (version_compare(PHP_VERSION, '7.4', '>=')) {
+ throw new UnexpectedValueException();
+ }
+ else {
+ drupal_trigger_fatal_error('Unexpected Value');
+ }
+ }
+ if (count($this->insertValues)) {
foreach ($this->insertValues as $insert_values) {
$placeholders = array();
diff --git a/includes/database/prefetch.inc b/includes/database/prefetch.inc
index 2a0bd55ce1..d9952683ca 100644
--- a/includes/database/prefetch.inc
+++ b/includes/database/prefetch.inc
@@ -293,6 +293,15 @@ class DatabaseStatementPrefetch implements Iterator, DatabaseStatementInterface
$class_name = $this->fetchOptions['class'];
}
if (count($this->fetchOptions['constructor_args'])) {
+ // Verify the current db connection to avoid this code being called
+ // in an inappropriate context.
+ $db_connection_options = Database::getConnection()->getConnectionOptions();
+ $defaults = array('sqlite', 'oracle');
+ $extras = variable_get('database_statement_prefetch_valid_db_drivers', array());
+ $valid_db_drivers = array_merge($defaults, $extras);
+ if (!in_array($db_connection_options['driver'], $valid_db_drivers)) {
+ throw new BadMethodCallException();
+ }
$reflector = new ReflectionClass($class_name);
$result = $reflector->newInstanceArgs($this->fetchOptions['constructor_args']);
}
diff --git a/includes/database/query.inc b/includes/database/query.inc
index 1c33ab4f80..5a6642a51c 100644
--- a/includes/database/query.inc
+++ b/includes/database/query.inc
@@ -1190,6 +1190,15 @@ class UpdateQuery extends Query implements QueryConditionInterface {
* The prepared statement.
*/
public function __toString() {
+ if (!is_array($this->expressionFields) || !is_array($this->fields)) {
+ if (version_compare(PHP_VERSION, '7.4', '>=')) {
+ throw new UnexpectedValueException();
+ }
+ else {
+ drupal_trigger_fatal_error('Unexpected Value');
+ }
+ }
+
// Create a sanitized comment string to prepend to the query.
$comments = $this->connection->makeComment($this->comments);
diff --git a/includes/database/sqlite/database.inc b/includes/database/sqlite/database.inc
index 2cf83ccb55..27a16f09b8 100644
--- a/includes/database/sqlite/database.inc
+++ b/includes/database/sqlite/database.inc
@@ -134,6 +134,9 @@ class DatabaseConnection_sqlite extends DatabaseConnection {
*/
public function __destruct() {
if ($this->tableDropped && !empty($this->attachedDatabases)) {
+ if (!is_array($this->attachedDatabases)) {
+ throw new UnexpectedValueException();
+ }
foreach ($this->attachedDatabases as $prefix) {
// Check if the database is now empty, ignore the internal SQLite tables.
try {
diff --git a/modules/overlay/overlay-parent.js b/modules/overlay/overlay-parent.js
index efb26370c5..0d41fadcc5 100644
--- a/modules/overlay/overlay-parent.js
+++ b/modules/overlay/overlay-parent.js
@@ -229,7 +229,7 @@ Drupal.overlay.destroy = function () {
*/
Drupal.overlay.redirect = function (url) {
// Create a native Link object, so we can use its object methods.
- var link = $(url.link(url)).get(0);
+ var link = $("").attr("href", url).get(0);
// If the link is already open, force the hashchange event to simulate reload.
if (window.location.href == link.href) {
@@ -865,7 +865,7 @@ Drupal.overlay.resetActiveClass = function(activePath) {
Drupal.overlay.getPath = function (link, ignorePathFromQueryString) {
if (typeof link == 'string') {
// Create a native Link object, so we can use its object methods.
- link = $(link.link(link)).get(0);
+ link = $("").attr("href", link).get(0);
}
var path = link.pathname;
diff --git a/modules/system/system.install b/modules/system/system.install
index 6221d30faa..76f5473d08 100644
--- a/modules/system/system.install
+++ b/modules/system/system.install
@@ -3432,6 +3432,13 @@ function system_update_7087() {
}
}
+/**
+ * Clear caches as registry has been altered.
+ */
+function system_update_7088() {
+ // Empty update to clear caches.
+}
+
/**
* @} End of "defgroup updates-7.x-extra".
* The next series of updates should start at 8000.
diff --git a/modules/system/system.module b/modules/system/system.module
index 9d7422f53c..4986aa5904 100644
--- a/modules/system/system.module
+++ b/modules/system/system.module
@@ -4139,3 +4139,11 @@ function system_file_download($uri) {
}
}
}
+
+/**
+ * Implements hook_registry_files_alter
+ */
+function system_registry_files_alter(&$files, $modules) {
+ // Database drivers that use DatabaseStatementPrefetch must include this file.
+ unset($files['includes/database/prefetch.inc']);
+}