# frozen_string_literal: true # # ronin-vulns - A Ruby library for blind vulnerability testing. # # Copyright (c) 2022-2023 Hal Brodigan (postmodern.mod3 at gmail.com) # # ronin-vulns is free software: you can redistribute it and/or modify # it under the terms of the GNU Lesser General Public License as published # by the Free Software Foundation, either version 3 of the License, or # (at your option) any later version. # # ronin-vulns is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public License # along with ronin-vulns. If not, see . # require 'ronin/vulns/lfi' require 'ronin/vulns/rfi' require 'ronin/vulns/sqli' require 'ronin/vulns/ssti' require 'ronin/vulns/reflected_xss' require 'ronin/vulns/open_redirect' module Ronin module Vulns # # Top-level module which scans a URL for all web vulnerabilities. # # ## Examples # # require 'ronin/vulns/url_scanner' # # Ronin::Vulns::URLScanner.scan(url) do |vuln| # # ... # end # # vuln = Ronin::Vulns::URLScanner.test(url) # module URLScanner # # Scans a URL for web vulnerabilities. # # @param [URI::HTTP, String] url # The URL to test or exploit. # # @option kwargs [String, Symbol, nil] :query_param # The query param to test or exploit. # # @option kwargs [String, Symbol, nil] :header_name # The HTTP Header name to test or exploit. # # @option kwargs [String, Symbol, nil] :cookie_param # The `Cookie:` param name to test or exploit. # # @option kwargs [String, Symbol, nil] :form_param # The form param name to test or exploit. # # @option kwargs [Ronin::Support::Network::HTTP, nil] :http # An HTTP session to use for testing the URL. # # @option kwargs [:copy, :delete, :get, :head, :lock, :mkcol, :move, # :options, :patch, :post, :propfind, :proppatch, :put, # :trace, :unlock] :request_method # The HTTP request mehtod for each request. # # @option kwargs [String, nil] :user # The user to authenticate as. # # @option kwargs [String, nil] :password # The password to authenticate with. # # @option kwargs [Hash{Symbol,String => String}, nil] :headers # Additional HTTP header names and values to add to the request. # # @option kwargs [String, Hash{String => String}, nil] :cookie # Additional `Cookie` header. If a `Hash` is given, it will be # converted to a `String` using `Ronin::Support::Network::HTTP::Cookie`. # # @option kwargs [Hash, String, nil] :form_data # The form data that may be sent in the body of the request. # # @option kwargs [String, nil] :referer # The optional HTTP `Referer` header to send with each request. # # @param [Hash{Symbol => Object}, false] lfi # Additional options for {LFI.scan}. # # @option lfi [:unix, :windows, nil] :os (:unix) # Operating System to specifically target. # # @option lfi [Integer] :depth (6) # Number of directories to escape up. # # @option lfi [:null_byte, :double_escape, :base64, :rot13, :zlib, nil] :filter_bypass # Specifies which filter bypass technique to use. # # * `:null_byte - appends a `%00` null byte to the escaped path. # **Note:* this technique only works on PHP < 5.3. # * `:double_escape` - Double escapes the {LFI#escape_path} # (ex: `....//....//`). # * `:base64` - Base64 encodes the included local file. # * `:rot13` - ROT13 encodes the included local file. # * `:zlib` - Zlib compresses and Base64 encodes the included local # file. # # @param [Hash{Symbol => Object}, false] rfi # Additional options for {RFI.scan}. # # @option rfi [:null_byte, :double_encode, nil] :filter_bypass # Specifies which filter bypass technique to use. # * `:double_encode` - will cause the inclusion URL to be URI escaped # twice. # * `:suffix_escape` - escape any appended suffix (ex: `param + ".php"`) # by adding a URI fragment character (`#`) to the end of the RFI # script URL. The fragment component of the URI is not sent to the # web server. # * `:null_byte` - will cause the inclusion URL to be appended with a # `%00` character. **Note:* this technique only works on PHP < 5.3. # # @option rfi [String, URI::HTTP, nil] :test_script_url # The URL of the RFI test script. If not specified, it will default to # {RFI.test_script_for}. # # @param [Hash{Symbol => Object}, false] sqli # Additional options for {SQLI.scan}. # # @option sqli [Boolean] :escape_quote (false) # Specifies whether to escape a quoted string value. # # @option sqli [Boolean] :escape_parens (false) # Specifies whether to escape parenthesis. # # @option sqli [Boolean] :terminate (false) # Specifies whether to terminate the SQL statement with `--`. # # @param [Hash{Symbol => Object}, false] ssti # Additional options for {SSTI.scan}. # # @option ssti [Proc, nil] :escape # How to escape a given payload. Either a proc that will accept a String # and return a String, or `nil` to indicate that the payload will not # be escaped. # # @option ssti [(String, String)] :test # The test payload and expected result to check for when testing the URL # for SSTI. # # @param [Hash{Symbol => Object}, false] reflected_xss # Additional options for {ReflectedXSS.scan}. # # @param [Hash{Symbol => Object}, false] open_redirect # Additional options for {OpenRedirect.scan}. # # @option open_redirect [String] :test_url (OpenRedirect.random_test_url) # The desired redirect URL to test the URL with. # # @yield [vuln] # If a block is given it will be yielded each discovered web # vulnerability. # # @yieldparam [LFI, RFI, SQLI, SSTI, ReflectedXSS, OpenRedirect] vuln # A discovered web vulnerability in the URL. # # @return [Array] # All discovered Web vulnerabilities. # def self.scan(url, lfi: {}, rfi: {}, sqli: {}, ssti: {}, reflected_xss: {}, open_redirect: {}, **kwargs, &block) vulns = [] if lfi vulns.concat(LFI.scan(url,**kwargs,**lfi,&block)) end if rfi vulns.concat(RFI.scan(url,**kwargs,**rfi,&block)) end if sqli vulns.concat(SQLI.scan(url,**kwargs,**sqli,&block)) end if ssti vulns.concat(SSTI.scan(url,**kwargs,**ssti,&block)) end if reflected_xss vulns.concat(ReflectedXSS.scan(url,**kwargs,**reflected_xss,&block)) end if open_redirect vulns.concat(OpenRedirect.scan(url,**kwargs,**open_redirect,&block)) end return vulns end # # Tests the URL for a Web vulnerability and returns the first found # vulnerability. # # @param [URI::HTTP, String] url # The URL to test. # # @param [Hash{Symbol => Object}] kwargs # Additional keyword arguments for {scan}. # # @return [LFI, RFI, SQLI, SSTI, ReflectedXSS, OpenRedirect, nil] # The first discovered web vulnerability or `nil` if no vulnerabilities # were discovered. # def self.test(url,**kwargs) scan(url,**kwargs) do |vuln| return vuln end return nil end end end end