HELLO v3!!!
This commit is contained in:
74
lib/wpscan/target/platform/wordpress.rb
Normal file
74
lib/wpscan/target/platform/wordpress.rb
Normal file
@@ -0,0 +1,74 @@
|
||||
%w[custom_directories].each do |required|
|
||||
require "wpscan/target/platform/wordpress/#{required}"
|
||||
end
|
||||
|
||||
module WPScan
|
||||
class Target < CMSScanner::Target
|
||||
module Platform
|
||||
# Some WordPress specific implementation
|
||||
module WordPress
|
||||
include CMSScanner::Target::Platform::PHP
|
||||
|
||||
WORDPRESS_PATTERN = %r{/(?:(?:wp-content/(?:themes|(?:mu\-)?plugins|uploads))|wp-includes)/}i
|
||||
|
||||
# These methods are used in the associated interesting_findings finders
|
||||
# to keep the boolean state of the finding rather than re-check the whole thing again
|
||||
attr_accessor :multisite, :registration_enabled, :mu_plugins
|
||||
alias multisite? multisite
|
||||
alias registration_enabled? registration_enabled
|
||||
alias mu_plugins? mu_plugins
|
||||
|
||||
# @return [ Boolean ]
|
||||
def wordpress?
|
||||
# res = Browser.get(url)
|
||||
|
||||
in_scope_urls(homepage_res) do |url|
|
||||
return true if Addressable::URI.parse(url).path.match(WORDPRESS_PATTERN)
|
||||
end
|
||||
|
||||
homepage_res.html.css('meta[name="generator"]').each do |node|
|
||||
return true if node['content'] =~ /wordpress/i
|
||||
end
|
||||
|
||||
return true unless comments_from_page(/wordpress/i, homepage_res).empty?
|
||||
|
||||
false
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def registration_url
|
||||
multisite? ? url('wp-signup.php') : url('wp-login.php?action=register')
|
||||
end
|
||||
|
||||
def wordpress_hosted?
|
||||
uri.host =~ /wordpress.com$/i ? true : false
|
||||
end
|
||||
|
||||
# @param [ String ] username
|
||||
# @param [ String ] password
|
||||
#
|
||||
# @return [ Typhoeus::Response ]
|
||||
def do_login(username, password)
|
||||
login_request(username, password).run
|
||||
end
|
||||
|
||||
# @param [ String ] username
|
||||
# @param [ String ] password
|
||||
#
|
||||
# @return [ Typhoeus::Request ]
|
||||
def login_request(username, password)
|
||||
Browser.instance.forge_request(
|
||||
login_url,
|
||||
method: :post,
|
||||
body: { log: username, pwd: password }
|
||||
)
|
||||
end
|
||||
|
||||
# @return [ String ] The URL to the login page
|
||||
def login_url
|
||||
url('wp-login.php')
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
108
lib/wpscan/target/platform/wordpress/custom_directories.rb
Normal file
108
lib/wpscan/target/platform/wordpress/custom_directories.rb
Normal file
@@ -0,0 +1,108 @@
|
||||
module WPScan
|
||||
class Target < CMSScanner::Target
|
||||
module Platform
|
||||
# wp-content & plugins directory implementation
|
||||
module WordPress
|
||||
def content_dir=(dir)
|
||||
@content_dir = dir.chomp('/')
|
||||
end
|
||||
|
||||
def plugins_dir=(dir)
|
||||
@plugins_dir = dir.chomp('/')
|
||||
end
|
||||
|
||||
# @return [ String ] The wp-content directory
|
||||
def content_dir
|
||||
unless @content_dir
|
||||
escaped_url = Regexp.escape(url).gsub(/https?/i, 'https?')
|
||||
pattern = %r{#{escaped_url}(.+?)\/(?:themes|plugins|uploads|cache)\/}i
|
||||
|
||||
in_scope_urls(homepage_res) do |url|
|
||||
return @content_dir = Regexp.last_match[1] if url.match(pattern)
|
||||
end
|
||||
end
|
||||
|
||||
@content_dir
|
||||
end
|
||||
|
||||
# @return [ Addressable::URI ]
|
||||
def content_uri
|
||||
uri.join("#{content_dir}/")
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def content_url
|
||||
content_uri.to_s
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def plugins_dir
|
||||
@plugins_dir ||= "#{content_dir}/plugins"
|
||||
end
|
||||
|
||||
# @return [ Addressable::URI ]
|
||||
def plugins_uri
|
||||
uri.join("#{plugins_dir}/")
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def plugins_url
|
||||
plugins_uri.to_s
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def themes_dir
|
||||
@themes_dir ||= "#{content_dir}/themes"
|
||||
end
|
||||
|
||||
# @return [ Addressable::URI ]
|
||||
def themes_uri
|
||||
uri.join("#{themes_dir}/")
|
||||
end
|
||||
|
||||
# @return [ String ]
|
||||
def themes_url
|
||||
themes_uri.to_s
|
||||
end
|
||||
|
||||
# TODO: Factorise the code and the content_dir one ?
|
||||
# @return [ String, False ] String of the sub_dir found, false otherwise
|
||||
# @note: nil can not be returned here, otherwise if there is no sub_dir
|
||||
# the check would be done each time
|
||||
def sub_dir
|
||||
unless @sub_dir
|
||||
escaped_url = Regexp.escape(url).gsub(/https?/i, 'https?')
|
||||
pattern = %r{#{escaped_url}(.+?)\/(?:xmlrpc\.php|wp\-includes\/)}i
|
||||
|
||||
in_scope_urls(homepage_res) do |url|
|
||||
return @sub_dir = Regexp.last_match[1] if url.match(pattern)
|
||||
end
|
||||
|
||||
@sub_dir = false
|
||||
end
|
||||
|
||||
@sub_dir
|
||||
end
|
||||
|
||||
# Override of the WebSite#url to consider the custom WP directories
|
||||
#
|
||||
# @param [ String ] path Optional path to merge with the uri
|
||||
#
|
||||
# @return [ String ]
|
||||
def url(path = nil)
|
||||
return @uri.to_s unless path
|
||||
|
||||
if path =~ %r{wp\-content/plugins}i
|
||||
path.gsub!('wp-content/plugins', plugins_dir)
|
||||
elsif path =~ /wp\-content/i
|
||||
path.gsub!('wp-content', content_dir)
|
||||
elsif path[0] != '/' && sub_dir
|
||||
path = "#{sub_dir}/#{path}"
|
||||
end
|
||||
|
||||
super(path)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
Reference in New Issue
Block a user