jenkins-bot has submitted this change and it was merged.

Change subject: Make allowing site-wide styles on restricted special pages a 
config option
......................................................................


Make allowing site-wide styles on restricted special pages a config option

This mostly reverts commit 614d7e5c274d927f99bfc52ac3a1e6c7e5902408.

Many wikis use MediaWiki:Common.css and associated pages to create a
custom "theme" for their wiki, which would no longer load on login
or preference pages, creating an inconsistent UI.

This re-adds the difference in module origin for different types
(styles, scripts, etc.), and now OutputPage::disallowUserJs()
checks the value of the "AllowSiteCSSOnRestrictedPages" config setting
to determine whether to allow site-wide CSS styles or not.

By default this feature is disabled to be secure by default.

Bug: 71621
Change-Id: I1bf4dd1845b6952c3985e179fbea48181ffb8907
---
M includes/DefaultSettings.php
M includes/OutputPage.php
2 files changed, 62 insertions(+), 36 deletions(-)

Approvals:
  Legoktm: Looks good to me, approved
  jenkins-bot: Verified



diff --git a/includes/DefaultSettings.php b/includes/DefaultSettings.php
index fe73044..4960ab6 100644
--- a/includes/DefaultSettings.php
+++ b/includes/DefaultSettings.php
@@ -2688,6 +2688,19 @@
  */
 $wgResourceLoaderExperimentalAsyncLoading = false;
 
+/**
+ * Whether to allow site-wide CSS (MediaWiki:Common.css and friends) on
+ * restricted pages like Special:UserLogin or Special:Preferences where
+ * JavaScript is disabled for security reasons. As it is possible to
+ * execute JavaScript through CSS, setting this to true opens up a
+ * potential security hole. Some sites may "skin" their wiki by using
+ * site-wide CSS, causing restricted pages to look unstyled and different
+ * from the rest of the site.
+ *
+ * @since 1.25
+ */
+$wgAllowSiteCSSOnRestrictedPages = false;
+
 /** @} */ # End of resource loader settings }
 
 
diff --git a/includes/OutputPage.php b/includes/OutputPage.php
index 869a265..00a9c1a 100644
--- a/includes/OutputPage.php
+++ b/includes/OutputPage.php
@@ -137,11 +137,14 @@
        var $mFeedLinksAppendQuery = null;
 
        /**
-        * @var int
-        * The level of 'untrustworthiness' allowed for modules loaded on this 
page.
+        * @var array
+        * What level of 'untrustworthiness' is allowed in CSS/JS modules 
loaded on this page?
         * @see ResourceLoaderModule::$origin
+        * ResourceLoaderModule::ORIGIN_ALL is assumed unless overridden;
         */
-       protected $mAllowedModuleOrigin = ResourceLoaderModule::ORIGIN_ALL;
+       protected $mAllowedModules = array(
+               ResourceLoaderModule::TYPE_COMBINED => 
ResourceLoaderModule::ORIGIN_ALL,
+       );
 
        /**
         * @EasterEgg I just love the name for this self documenting variable.
@@ -1194,13 +1197,31 @@
        }
 
        /**
-        * Restrict the page to loading modules bundled the software.
+        * Do not allow scripts which can be modified by wiki users to load on 
this page;
+        * only allow scripts bundled with, or generated by, the software.
+        * Site-wide styles are controlled by a config setting, since they can 
be
+        * used to create a custom skin/theme, but not user-specific ones.
         *
-        * Disallows the queue to contain any modules which can be modified by 
wiki
-        * users to load on this page.
+        * @todo this should be given a more accurate name
         */
        public function disallowUserJs() {
-               $this->reduceAllowedModuleOrigin( 
ResourceLoaderModule::ORIGIN_CORE_INDIVIDUAL );
+               global $wgAllowSiteCSSOnRestrictedPages;
+               $this->reduceAllowedModules(
+                       ResourceLoaderModule::TYPE_SCRIPTS,
+                       ResourceLoaderModule::ORIGIN_CORE_INDIVIDUAL
+               );
+
+               // Site-wide styles are controlled by a config setting, see bug 
71621
+               // for background on why. User styles are never allowed.
+               if (  $wgAllowSiteCSSOnRestrictedPages ) {
+                       $styleOrigin = 
ResourceLoaderModule::ORIGIN_USER_SITEWIDE;
+               } else {
+                       $styleOrigin = 
ResourceLoaderModule::ORIGIN_CORE_INDIVIDUAL;
+               }
+               $this->reduceAllowedModules(
+                       ResourceLoaderModule::TYPE_STYLES,
+                       $styleOrigin
+               );
        }
 
        /**
@@ -1219,40 +1240,31 @@
         * Get the level of JavaScript / CSS untrustworthiness allowed on this 
page.
         *
         * @see ResourceLoaderModule::$origin
-        * @param string $type Unused: Module origin allowance used to be 
fragmented by
-        *  ResourceLoaderModule TYPE_ constants.
-        * @return Int ResourceLoaderModule ORIGIN_ class constant
+        * @param string $type ResourceLoaderModule TYPE_ constant
+        * @return nt ResourceLoaderModule ORIGIN_ class constant
         */
-       public function getAllowedModules( $type = null ) {
-               return $this->mAllowedModuleOrigin;
+       public function getAllowedModules( $type ) {
+               if ( $type == ResourceLoaderModule::TYPE_COMBINED ) {
+                       return min( array_values( $this->mAllowedModules ) );
+               } else {
+                       return isset( $this->mAllowedModules[$type] )
+                               ? $this->mAllowedModules[$type]
+                               : ResourceLoaderModule::ORIGIN_ALL;
+               }
        }
 
        /**
         * Set the highest level of CSS/JS untrustworthiness allowed
         *
         * @deprecated since 1.24 Raising level of allowed untrusted content is 
no longer supported.
-        *  Use reduceAllowedModuleOrigin() instead.
+        *  Use reduceAllowedModules() instead.
         *
-        * @param  $type String ResourceLoaderModule TYPE_ constant
-        * @param int $level ResourceLoaderModule ORIGIN_ constant
+        * @param string $type ResourceLoaderModule TYPE_ constant
+        * @param int $level ResourceLoaderModule class constant
         */
        public function setAllowedModules( $type, $level ){
                wfDeprecated( __METHOD__, '1.24' );
-               $this->reduceAllowedModuleOrigin( $level );
-       }
-
-       /**
-        * Limit the highest level of CSS/JS untrustworthiness allowed.
-        *
-        * @deprecated since 1.24 Module allowance is no longer fragmented by 
content type.
-        *  Use reduceAllowedModuleOrigin() instead.
-        *
-        * @param string $type ResourceLoaderModule TYPE_ constant
-        * @param int $level ResourceLoaderModule ORIGIN_ class constant
-        */
-       public function reduceAllowedModules( $type, $level ){
-               wfDeprecated( __METHOD__, '1.24' );
-               $this->reduceAllowedModuleOrigin( $level );
+               $this->reduceAllowedModules( type, $level );
        }
 
        /**
@@ -1261,10 +1273,11 @@
         * If passed the same or a higher level than the current level of 
untrustworthiness set, the
         * level will remain unchanged.
         *
+        * @param string $type
         * @param int $level ResourceLoaderModule class constant
         */
-       public function reduceAllowedModuleOrigin( $level ) {
-               $this->mAllowedModuleOrigin = min( $this->mAllowedModuleOrigin, 
$level );
+       public function reduceAllowedModules( $type, $level ) {
+               $this->mAllowedModules[$type] = min( $this->getAllowedModules( 
$type ), $level );
        }
 
        /**
@@ -2671,7 +2684,7 @@
                                // Automatically select style/script elements
                                if ( $only === 
ResourceLoaderModule::TYPE_STYLES ) {
                                        $link = Html::linkedStyle( $url );
-                               } else if ( $loadCall ) { 
+                               } else if ( $loadCall ) {
                                        $link = Html::inlineScript(
                                                
ResourceLoader::makeLoaderConditionalScript(
                                                        Xml::encodeJsCall( 
'mw.loader.load', array( $url, 'text/javascript', true ) )
@@ -2699,7 +2712,7 @@
         */
        function getHeadScripts() {
                global $wgResourceLoaderExperimentalAsyncLoading;
-               
+
                // Startup - this will immediately load jquery and mediawiki 
modules
                $scripts = $this->makeResourceLoaderLink( 'startup', 
ResourceLoaderModule::TYPE_SCRIPTS, true );
 
@@ -2731,7 +2744,7 @@
                                )
                        );
                }
-               
+
                if ( $wgResourceLoaderExperimentalAsyncLoading ) {
                        $scripts .= $this->getScriptsForBottomQueue( true );
                }
@@ -3288,7 +3301,7 @@
                                $otherTags .= $this->makeResourceLoaderLink( 
'user', ResourceLoaderModule::TYPE_STYLES, false,
                                        array( 'excludepage' => 
$this->getTitle()->getPrefixedDBkey() )
                                );
-                               
+
                                // Load the previewed CSS
                                // If needed, Janus it first. This is 
user-supplied CSS, so it's
                                // assumed to be right for the content language 
directionality.

-- 
To view, visit https://gerrit.wikimedia.org/r/175671
To unsubscribe, visit https://gerrit.wikimedia.org/r/settings

Gerrit-MessageType: merged
Gerrit-Change-Id: I1bf4dd1845b6952c3985e179fbea48181ffb8907
Gerrit-PatchSet: 2
Gerrit-Project: mediawiki/core
Gerrit-Branch: REL1_19
Gerrit-Owner: Mglaser <[email protected]>
Gerrit-Reviewer: Daniel Friesen <[email protected]>
Gerrit-Reviewer: Legoktm <[email protected]>
Gerrit-Reviewer: Mglaser <[email protected]>
Gerrit-Reviewer: TTO <[email protected]>
Gerrit-Reviewer: jenkins-bot <>

_______________________________________________
MediaWiki-commits mailing list
[email protected]
https://lists.wikimedia.org/mailman/listinfo/mediawiki-commits

Reply via email to