r6663 MediaWiki - Code Review archive

Repository:MediaWiki
Revision:r6662‎ | r6663 | r6664 >
Date:23:31, 12 December 2004
Author:vibber
Status:old
Tags:
Comment:
* Enhance upload extension blacklist to protect against vulnerable Apache configurations
Modified paths:
  • /branches/REL1_3/phase3/RELEASE-NOTES (modified) (history)
  • /branches/REL1_3/phase3/includes/SpecialUpload.php (modified) (history)

Diff [purge]

Index: branches/REL1_3/phase3/includes/SpecialUpload.php
@@ -156,14 +156,18 @@
157157 # Chop off any directories in the given filename
158158 $basename = basename( $this->mOname );
159159
160 - if( preg_match( '/^(.*)\.([^.]*)$/', $basename, $matches ) ) {
161 - $partname = $matches[1];
162 - $ext = $matches[2];
 160+ /**
 161+ * We'll want to blacklist against *any* 'extension', and use
 162+ * only the final one for the whitelist.
 163+ */
 164+ list( $partname, $ext ) = $this->splitExtensions( $basename );
 165+ if( count( $ext ) ) {
 166+ $finalExt = $ext[count( $ext ) - 1];
163167 } else {
164 - $partname = $basename;
165 - $ext = '';
 168+ $finalExt = '';
166169 }
167 -
 170+ $fullExt = implode( '.', $ext );
 171+
168172 if ( strlen( $partname ) < 3 ) {
169173 $this->mainUploadForm( wfMsg( 'minlength' ) );
170174 return;
@@ -192,9 +196,10 @@
193197 /* Don't allow users to override the blacklist */
194198 global $wgStrictFileExtensions;
195199 global $wgFileExtensions, $wgFileBlacklist;
196 - if( $this->checkFileExtension( $ext, $wgFileBlacklist ) ||
197 - ($wgStrictFileExtensions && !$this->checkFileExtension( $ext, $wgFileExtensions ) ) ) {
198 - return $this->uploadError( wfMsg( 'badfiletype', htmlspecialchars( $ext ) ) );
 200+ if( $this->checkFileExtensionList( $ext, $wgFileBlacklist ) ||
 201+ ($wgStrictFileExtensions &&
 202+ !$this->checkFileExtension( $finalExt, $wgFileExtensions ) ) ) {
 203+ return $this->uploadError( wfMsg( 'badfiletype', htmlspecialchars( $fullExt ) ) );
199204 }
200205
201206 /**
@@ -202,7 +207,7 @@
203208 * type but it's corrupt or data of the wrong type, we should
204209 * probably not accept it.
205210 */
206 - if( !$this->verify( $this->mUploadTempName, $ext ) ) {
 211+ if( !$this->verify( $this->mUploadTempName, $finalExt ) ) {
207212 return $this->uploadError( wfMsg( 'uploadcorrupt' ) );
208213 }
209214
@@ -217,8 +222,8 @@
218223
219224 global $wgCheckFileExtensions;
220225 if ( $wgCheckFileExtensions ) {
221 - if ( ! $this->checkFileExtension( $ext, $wgFileExtensions ) ) {
222 - $warning .= '<li>'.wfMsg( 'badfiletype', htmlspecialchars( $ext ) ).'</li>';
 226+ if ( ! $this->checkFileExtension( $finalExt, $wgFileExtensions ) ) {
 227+ $warning .= '<li>'.wfMsg( 'badfiletype', htmlspecialchars( $fullExt ) ).'</li>';
223228 }
224229 }
225230
@@ -535,6 +540,20 @@
536541 /* -------------------------------------------------------------- */
537542
538543 /**
 544+ * Split a file into a base name and all dot-delimited 'extensions'
 545+ * on the end. Some web server configurations will fall back to
 546+ * earlier pseudo-'extensions' to determine type and execute
 547+ * scripts, so the blacklist needs to check them all.
 548+ *
 549+ * @return array
 550+ */
 551+ function splitExtensions( $filename ) {
 552+ $bits = explode( '.', $filename );
 553+ $basename = array_shift( $bits );
 554+ return array( $basename, $bits );
 555+ }
 556+
 557+ /**
539558 * Perform case-insensitive match against a list of file extensions.
540559 * Returns true if the extension is in the list.
541560 *
@@ -547,6 +566,23 @@
548567 }
549568
550569 /**
 570+ * Perform case-insensitive match against a list of file extensions.
 571+ * Returns true if any of the extensions are in the list.
 572+ *
 573+ * @param array $ext
 574+ * @param array $list
 575+ * @return bool
 576+ */
 577+ function checkFileExtensionList( $ext, $list ) {
 578+ foreach( $ext as $e ) {
 579+ if( in_array( strtolower( $e ), $list ) ) {
 580+ return true;
 581+ }
 582+ }
 583+ return false;
 584+ }
 585+
 586+ /**
551587 * Returns false if the file is of a known type but can't be recognized,
552588 * indicating a corrupt file.
553589 * Returns true otherwise; unknown file types are not checked if given
Index: branches/REL1_3/phase3/RELEASE-NOTES
@@ -3,8 +3,24 @@
44 Security reminder: MediaWiki does not require PHP's register_globals
55 setting since version 1.2.0. If you have it on, turn it *off* if you can.
66
7 -== Version 1.3.9, ****-**-** ==
 7+== Version 1.3.9, 2004-12-12 ==
88
 9+MediaWiki 1.3.9 is a security and bug fix release.
 10+
 11+A flaw in upload handling has been found which may allow upload and
 12+execution of arbitrary scripts with the permissions of the web server.
 13+Only wikis that have enabled uploads and have a vulnerable Apache
 14+configuration will be affected, but to be safe all wikis should upgrade.
 15+
 16+Wikis with uploads available should either disable uploads or upgrade to
 17+1.3.9 immediately; if other files are customized and require merging
 18+changes, includes/SpecialUpload.php may be replaced individually to add
 19+the fix.
 20+
 21+(It is also recommended to configure your web server to disable script
 22+execution in the 'images' subdirectory where uploads are placed, which
 23+prevents most attacks even if the wiki fails.)
 24+
925 Changes from 1.3.8:
1026 * Backported "Templates used in this page"-feature of EditPage
1127 * Allow "MySkin" as a default skin.
@@ -12,7 +28,10 @@
1329 * (bug 1010) fix broken Commons image link on Classic & Cologne Blue
1430 * (bug 1004) Norsk language names for interwiki links changed,
1531 Nauruan language name changed
 32+* Enhance upload extension blacklist to protect against vulnerable
 33+ Apache configurations
1634
 35+
1736 == Version 1.3.8, 2004-11-15 ==
1837
1938 MediaWiki 1.3.8 is a bugfix release. Those running wikis with uploads

Status & tagging log