diff --git a/.wordpress-org/blueprints/blueprint.json b/.wordpress-org/blueprints/blueprint.json
index 3f11dd67..d52cb449 100644
--- a/.wordpress-org/blueprints/blueprint.json
+++ b/.wordpress-org/blueprints/blueprint.json
@@ -15,7 +15,7 @@
"step": "installPlugin",
"pluginZipFile": {
"resource": "url",
- "url": "https:\/\/downloads.wordpress.org\/plugin\/ultimate-member.2.11.1.zip"
+ "url": "https:\/\/downloads.wordpress.org\/plugin\/ultimate-member.2.11.2.zip"
},
"options": {
"activate": true
diff --git a/README.md b/README.md
index 3855d9de..6b6ea1e9 100644
--- a/README.md
+++ b/README.md
@@ -44,7 +44,7 @@ GNU Version 2 or Any Later Version
### IMPORTANT: PLEASE UPDATE THE PLUGIN TO AT LEAST VERSION 2.6.7 IMMEDIATELY. VERSION 2.6.7 PATCHES SECURITY PRIVILEGE ESCALATION VULNERABILITY. PLEASE SEE [THIS ARTICLE](https://docs.ultimatemember.com/article/1866-security-incident-update-and-recommended-actions) FOR MORE INFORMATION
-[Official Release Version: 2.11.1](https://github.com/ultimatemember/ultimatemember/releases/tag/2.11.1).
+[Official Release Version: 2.11.2](https://github.com/ultimatemember/ultimatemember/releases/tag/2.11.2).
## Changelog
diff --git a/changelog.txt b/changelog.txt
index 9862c572..8b0d1c9d 100644
--- a/changelog.txt
+++ b/changelog.txt
@@ -1,5 +1,11 @@
== Changelog ==
+= 2.11.2 January xx, 2026 =
+
+* Bugfixes:
+
+ - Fixed: Security issue CVE ID: CVE-2025-15064. Deprecated ability to use HTML inside the user description.
+
= 2.11.1 December 16, 2025 =
* Enhancements:
diff --git a/includes/core/class-form.php b/includes/core/class-form.php
index 8a8c6e3e..a2bbc284 100644
--- a/includes/core/class-form.php
+++ b/includes/core/class-form.php
@@ -843,26 +843,7 @@ if ( ! class_exists( 'um\core\Form' ) ) {
if ( ! empty( $field['html'] ) || ( UM()->profile()->get_show_bio_key( $form ) === $k && UM()->options()->get( 'profile_show_html_bio' ) ) ) {
$form[ $k ] = html_entity_decode( $form[ $k ] ); // required because WP_Editor send sometimes encoded content.
$form[ $k ] = self::maybe_apply_tidy( $form[ $k ], $field );
-
- $allowed_html = UM()->get_allowed_html( 'templates' );
- if ( empty( $allowed_html['iframe'] ) ) {
- $allowed_html['iframe'] = array(
- 'allow' => true,
- 'frameborder' => true,
- 'loading' => true,
- 'name' => true,
- 'referrerpolicy' => true,
- 'sandbox' => true,
- 'src' => true,
- 'srcdoc' => true,
- 'title' => true,
- 'width' => true,
- 'height' => true,
- 'allowfullscreen' => true,
- );
- }
- $form[ $k ] = wp_kses( strip_shortcodes( $form[ $k ] ), $allowed_html );
- add_filter( 'wp_kses_allowed_html', array( &$this, 'wp_kses_user_desc' ), 10, 2 );
+ $form[ $k ] = wp_kses( strip_shortcodes( $form[ $k ] ), UM()->get_allowed_html( 'templates' ) );
} else {
$form[ $k ] = sanitize_textarea_field( strip_shortcodes( $form[ $k ] ) );
}
@@ -983,27 +964,7 @@ if ( ! class_exists( 'um\core\Form' ) ) {
if ( ! empty( $custom_fields[ $description_key ]['html'] ) && $bio_html ) {
$form[ $description_key ] = html_entity_decode( $form[ $description_key ] ); // required because WP_Editor send sometimes encoded content.
$form[ $description_key ] = self::maybe_apply_tidy( $form[ $description_key ], $custom_fields[ $description_key ] );
-
- $allowed_html = UM()->get_allowed_html( 'templates' );
- if ( empty( $allowed_html['iframe'] ) ) {
- $allowed_html['iframe'] = array(
- 'allow' => true,
- 'frameborder' => true,
- 'loading' => true,
- 'name' => true,
- 'referrerpolicy' => true,
- 'sandbox' => true,
- 'src' => true,
- 'srcdoc' => true,
- 'title' => true,
- 'width' => true,
- 'height' => true,
- 'allowfullscreen' => true,
- );
- }
- $form[ $description_key ] = wp_kses( strip_shortcodes( $form[ $description_key ] ), $allowed_html );
-
- add_filter( 'wp_kses_allowed_html', array( &$this, 'wp_kses_user_desc' ), 10, 2 );
+ $form[ $description_key ] = wp_kses( strip_shortcodes( $form[ $description_key ] ), UM()->get_allowed_html( 'templates' ) );
} else {
$form[ $description_key ] = sanitize_textarea_field( strip_shortcodes( $form[ $description_key ] ) );
}
@@ -1012,26 +973,9 @@ if ( ! class_exists( 'um\core\Form' ) ) {
if ( ! $field_exists ) {
if ( $bio_html ) {
- $allowed_html = UM()->get_allowed_html( 'templates' );
- if ( empty( $allowed_html['iframe'] ) ) {
- $allowed_html['iframe'] = array(
- 'allow' => true,
- 'frameborder' => true,
- 'loading' => true,
- 'name' => true,
- 'referrerpolicy' => true,
- 'sandbox' => true,
- 'src' => true,
- 'srcdoc' => true,
- 'title' => true,
- 'width' => true,
- 'height' => true,
- 'allowfullscreen' => true,
- );
- }
- $form[ $description_key ] = wp_kses( strip_shortcodes( $form[ $description_key ] ), $allowed_html );
-
- add_filter( 'wp_kses_allowed_html', array( &$this, 'wp_kses_user_desc' ), 10, 2 );
+ $form[ $description_key ] = html_entity_decode( $form[ $description_key ] ); // required because WP_Editor send sometimes encoded content.
+ $form[ $description_key ] = self::maybe_apply_tidy( $form[ $description_key ], array() );
+ $form[ $description_key ] = wp_kses( strip_shortcodes( $form[ $description_key ] ), UM()->get_allowed_html( 'templates' ) );
} else {
$form[ $description_key ] = sanitize_textarea_field( strip_shortcodes( $form[ $description_key ] ) );
}
@@ -1042,30 +986,6 @@ if ( ! class_exists( 'um\core\Form' ) ) {
return $form;
}
- public function wp_kses_user_desc( $tags, $context ) {
- if ( 'user_description' === $context || 'pre_user_description' === $context ) {
- $allowed_html = UM()->get_allowed_html( 'templates' );
- if ( empty( $allowed_html['iframe'] ) ) {
- $allowed_html['iframe'] = array(
- 'allow' => true,
- 'frameborder' => true,
- 'loading' => true,
- 'name' => true,
- 'referrerpolicy' => true,
- 'sandbox' => true,
- 'src' => true,
- 'srcdoc' => true,
- 'title' => true,
- 'width' => true,
- 'height' => true,
- 'allowfullscreen' => true,
- );
- }
- $tags = $allowed_html;
- }
- return $tags;
- }
-
/**
* Display form type as Title
* @param string $mode
diff --git a/readme.txt b/readme.txt
index 497bcb29..df3581f8 100644
--- a/readme.txt
+++ b/readme.txt
@@ -6,7 +6,7 @@ Tags: community, member, membership, user-profile, user-registration
Requires PHP: 7.0
Requires at least: 6.2
Tested up to: 6.9
-Stable tag: 2.11.1
+Stable tag: 2.11.2
License: GPLv3
License URI: http://www.gnu.org/licenses/gpl-3.0.txt
@@ -167,6 +167,12 @@ No specific extensions are needed. But we highly recommended keep active these P
IMPORTANT: PLEASE UPDATE THE PLUGIN TO AT LEAST VERSION 2.6.7 IMMEDIATELY. VERSION 2.6.7 PATCHES SECURITY PRIVILEGE ESCALATION VULNERABILITY. PLEASE SEE [THIS ARTICLE](https://docs.ultimatemember.com/article/1866-security-incident-update-and-recommended-actions) FOR MORE INFORMATION
+= 2.11.2 2026-01-xx =
+
+**Bugfixes**
+
+* Fixed: Security issue CVE ID: CVE-2025-15064. Deprecated ability to use HTML inside the user description.
+
= 2.11.1 2025-12-16 =
**Enhancements**
@@ -209,6 +215,9 @@ IMPORTANT: PLEASE UPDATE THE PLUGIN TO AT LEAST VERSION 2.6.7 IMMEDIATELY. VERSI
== Upgrade Notice ==
+= 2.11.2 =
+This version fixes a security related bug. Upgrade immediately.
+
= 2.11.1 =
This version fixes a security related bug. Upgrade immediately.
diff --git a/ultimate-member.php b/ultimate-member.php
index 28be4e52..a3038838 100644
--- a/ultimate-member.php
+++ b/ultimate-member.php
@@ -3,7 +3,7 @@
* Plugin Name: Ultimate Member
* Plugin URI: http://ultimatemember.com/
* Description: The easiest way to create powerful online communities and beautiful user profiles with WordPress
- * Version: 2.11.1
+ * Version: 2.11.2
* Author: Ultimate Member
* Author URI: http://ultimatemember.com/
* License: GPLv3
@@ -41,3 +41,7 @@ define( 'UM_UPDATER_DEBUG', false ); // Set true then need to debug the upgrade
require_once 'includes/class-functions.php';
require_once 'includes/class-init.php';
+//
+//echo wp_kses( '', UM()->get_allowed_html( 'templates' ) );
+//echo wp_kses( '
', UM()->get_allowed_html( 'templates' ) );
+//exit;