CVE-2021-3783: Improper Neutralization of Input During Web Page Generation ('Cross-site Scripting') (CWE-79)
value: yourls is vulnerable to Improper Neutralization of Input During Web Page Generation ('Cross-site Scripting')
CWE description: The product does not neutralize or incorrectly neutralizes user-controllable input before it is placed in output that is used as a web page that is served to other users.
CVSS v3 base score: 6.1
Published: 2021-09-15T12:15Z
Repository: https://github.com/yourls/yourls
Language: PHP
Files changed: admin/upgrade.php, includes/functions-upgrade.php, includes/version.php
Commit date: 2021-09-09 15:05:50 +0200
Commit message: Sanitize user input in upgrade (#3055)


Diff: diff --git a/admin/upgrade.php b/admin/upgrade.php
index cf011b9b..81333244 100644
--- a/admin/upgrade.php
+++ b/admin/upgrade.php
@@ -26,12 +26,12 @@
 	        - update version & db_version in options, this is all done!
 	*/
 
 	// From what are we upgrading?
 	if ( isset( $_GET['oldver'] ) && isset( $_GET['oldsql'] ) ) {
-		$oldver = (string)( $_GET['oldver'] );
-		$oldsql = (string)( $_GET['oldsql'] );
+		$oldver = yourls_sanitize_version($_GET['oldver']);
+		$oldsql = (intval)($_GET['oldsql']);
 	} else {
 		list( $oldver, $oldsql ) = yourls_get_current_version_from_sql();
 	}
 
 	// To what are we upgrading ?
diff --git a/includes/functions-upgrade.php b/includes/functions-upgrade.php
index 7bc8760f..2de8e0e2 100644
--- a/includes/functions-upgrade.php
+++ b/includes/functions-upgrade.php
@@ -8,10 +8,23 @@
  * multiple SQL update during the dev cycle of the same Y0URLS version
  *
  */
 function yourls_upgrade( $step, $oldver, $newver, $oldsql, $newsql ) {
 
+    /**
+     *  Sanitize input. Two notes :
+     *  - they should already be sanitized in the caller, eg admin/upgrade.php
+     *    (but hey, let's make sure)
+     *  - some vars may not be used at the moment
+     *    (and this is ok, they are here in case a future upgrade procedure needs them)
+     */
+    $step   = intval($step);
+    $oldsql = intval($oldsql);
+    $newsql = intval($newsql);
+    $oldver = yourls_sanitize_version($oldver);
+    $newver = yourls_sanitize_version($newver);
+
     yourls_maintenance_mode(true);
 
     // special case for 1.3: the upgrade is a multi step procedure
 	if( $oldsql == 100 ) {
 		yourls_upgrade_to_14( $step );
diff --git a/includes/version.php b/includes/version.php
index c4339132..baa1a78d 100644
--- a/includes/version.php
+++ b/includes/version.php
@@ -1,12 +1,20 @@
 <?php
 /**
  * YOURLS version
  *
+ * Must be one of the following :
+ *    MAJOR.MINOR (eg 1.8)
+ *    MAJOR.MINOR.PATCH (1.8.1)
+ *    MAJOR.MINOR-SOMETHING (1.8-dev)
+ *    MAJOR.MINOR.PATCH-SOMETHING (1.8.1-donotuse)
+ *
  */
 define( 'YOURLS_VERSION', '1.8.3-dev' );
 
 /**
  * YOURLS DB version. Increments when changes are made to the DB schema, to trigger a DB update
  *
+ * Must be a string of an integer.
+ *
  */
 define( 'YOURLS_DB_VERSION', '506' );

Vulnerable code: 		$oldver = (string)( $_GET['oldver'] );
		$oldsql = (string)( $_GET['oldsql'] );
Fixed code: 		$oldver = yourls_sanitize_version($_GET['oldver']);
		$oldsql = (intval)($_GET['oldsql']);
    /**
     *  Sanitize input. Two notes :
     *  - they should already be sanitized in the caller, eg admin/upgrade.php
     *    (but hey, let's make sure)
     *  - some vars may not be used at the moment
     *    (and this is ok, they are here in case a future upgrade procedure needs them)
     */
    $step   = intval($step);
    $oldsql = intval($oldsql);
    $newsql = intval($newsql);
    $oldver = yourls_sanitize_version($oldver);
    $newver = yourls_sanitize_version($newver);

 * Must be one of the following :
 *    MAJOR.MINOR (eg 1.8)
 *    MAJOR.MINOR.PATCH (1.8.1)
 *    MAJOR.MINOR-SOMETHING (1.8-dev)
 *    MAJOR.MINOR.PATCH-SOMETHING (1.8.1-donotuse)
 *
 * Must be a string of an integer.
 *