pentest 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 195a88c8e21c3486bb9a1873e5009952b6b5948876f1329e18b0dabc4cfa247c
4
+ data.tar.gz: b8386287f2655eba62b96bb715676cb19572995904980ba3d2445713baff7ed8
5
+ SHA512:
6
+ metadata.gz: 2e7da539e2433c292b9be7f6cf937a63cfc3556f0ed8a4f801457ad26de60aacac276a599245985bb96bb2b686121e6d5b5fd43bbe3f36fdfd5959e1e86b7ba7
7
+ data.tar.gz: f7771f7d8ea746e4ae8bfbce8083d9612cb24dc9378c5c2f4aa9c66e892256cfbb0d19295bdd98de2df16483db252d10fae61e22ffdebedc41eceb551e08e493
@@ -0,0 +1,11 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /_yardoc/
4
+ /coverage/
5
+ /doc/
6
+ /pkg/
7
+ /spec/reports/
8
+ /tmp/
9
+
10
+ # rspec failure tracking
11
+ .rspec_status
data/.rspec ADDED
@@ -0,0 +1,3 @@
1
+ --format documentation
2
+ --color
3
+ --require spec_helper
@@ -0,0 +1,7 @@
1
+ ---
2
+ sudo: false
3
+ language: ruby
4
+ cache: bundler
5
+ rvm:
6
+ - 2.6.3
7
+ before_install: gem install bundler -v 1.17.2
data/Gemfile ADDED
@@ -0,0 +1,6 @@
1
+ source "https://rubygems.org"
2
+
3
+ git_source(:github) {|repo_name| "https://github.com/#{repo_name}" }
4
+
5
+ # Specify your gem's dependencies in pentest.gemspec
6
+ gemspec
@@ -0,0 +1,75 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ pentest (0.1.2)
5
+ arproxy
6
+ callsite
7
+ gda
8
+ nokogiri
9
+ pairwise
10
+ ruby_parser
11
+ term-ansicolor
12
+
13
+ GEM
14
+ remote: https://rubygems.org/
15
+ specs:
16
+ activemodel (6.0.0)
17
+ activesupport (= 6.0.0)
18
+ activerecord (6.0.0)
19
+ activemodel (= 6.0.0)
20
+ activesupport (= 6.0.0)
21
+ activesupport (6.0.0)
22
+ concurrent-ruby (~> 1.0, >= 1.0.2)
23
+ i18n (>= 0.7, < 2)
24
+ minitest (~> 5.1)
25
+ tzinfo (~> 1.1)
26
+ zeitwerk (~> 2.1, >= 2.1.8)
27
+ arproxy (0.2.6)
28
+ activerecord (>= 4.2.0)
29
+ callsite (0.0.11)
30
+ concurrent-ruby (1.1.5)
31
+ diff-lcs (1.3)
32
+ gda (1.1.0)
33
+ i18n (1.6.0)
34
+ concurrent-ruby (~> 1.0)
35
+ mini_portile2 (2.4.0)
36
+ minitest (5.11.3)
37
+ nokogiri (1.10.4)
38
+ mini_portile2 (~> 2.4.0)
39
+ pairwise (0.2.1)
40
+ rake (10.5.0)
41
+ rspec (3.8.0)
42
+ rspec-core (~> 3.8.0)
43
+ rspec-expectations (~> 3.8.0)
44
+ rspec-mocks (~> 3.8.0)
45
+ rspec-core (3.8.2)
46
+ rspec-support (~> 3.8.0)
47
+ rspec-expectations (3.8.4)
48
+ diff-lcs (>= 1.2.0, < 2.0)
49
+ rspec-support (~> 3.8.0)
50
+ rspec-mocks (3.8.1)
51
+ diff-lcs (>= 1.2.0, < 2.0)
52
+ rspec-support (~> 3.8.0)
53
+ rspec-support (3.8.2)
54
+ ruby_parser (3.13.1)
55
+ sexp_processor (~> 4.9)
56
+ sexp_processor (4.12.1)
57
+ term-ansicolor (1.7.1)
58
+ tins (~> 1.0)
59
+ thread_safe (0.3.6)
60
+ tins (1.21.1)
61
+ tzinfo (1.2.5)
62
+ thread_safe (~> 0.1)
63
+ zeitwerk (2.1.9)
64
+
65
+ PLATFORMS
66
+ ruby
67
+
68
+ DEPENDENCIES
69
+ bundler (~> 1.17)
70
+ pentest!
71
+ rake (~> 10.0)
72
+ rspec (~> 3.0)
73
+
74
+ BUNDLED WITH
75
+ 1.17.2
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2019 Koki Takahashi
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
@@ -0,0 +1,59 @@
1
+ # Pentest
2
+
3
+ Welcome to your new gem! In this directory, you'll find the files you need to be able to package up your Ruby library into a gem. Put your Ruby code in the file `lib/pentest`. To experiment with that code, run `bin/console` for an interactive prompt.
4
+
5
+ TODO: Delete this and the text above, and describe your gem
6
+
7
+ ## Prerequisite
8
+
9
+ * libgda
10
+
11
+ ### Windows
12
+
13
+ ### Mac
14
+
15
+ Please be reminded that you should link keg-only dependent libxml2.
16
+
17
+ ```
18
+ brew install libgda
19
+ brew link libxml2 --force
20
+ bundle install
21
+ ```
22
+
23
+ ### Ubuntu
24
+
25
+ ## Installation
26
+
27
+ Add this line to your application's Gemfile:
28
+
29
+ ```ruby
30
+ gem 'pentest'
31
+ ```
32
+
33
+ And then execute:
34
+
35
+ $ bundle
36
+
37
+ Or install it yourself as:
38
+
39
+ $ gem install pentest
40
+
41
+ ## Usage
42
+
43
+ ```
44
+ $ RAILS_ENV=test bundle exec pentest
45
+ ```
46
+
47
+ ## Development
48
+
49
+ After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake spec` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
50
+
51
+ To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
52
+
53
+ ## Contributing
54
+
55
+ Bug reports and pull requests are welcome on GitHub at https://github.com/[USERNAME]/pentest.
56
+
57
+ ## License
58
+
59
+ The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT).
@@ -0,0 +1,6 @@
1
+ require "bundler/gem_tasks"
2
+ require "rspec/core/rake_task"
3
+
4
+ RSpec::Core::RakeTask.new(:spec)
5
+
6
+ task :default => :spec
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "bundler/setup"
4
+ require "pentest"
5
+
6
+ # You can add fixtures and/or initialization code here to make experimenting
7
+ # with your gem easier. You can also use a different console, if you like.
8
+
9
+ # (If you use this, don't forget to add pry to your Gemfile!)
10
+ # require "pry"
11
+ # Pry.start
12
+
13
+ require "irb"
14
+ IRB.start(__FILE__)
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+ set -vx
5
+
6
+ bundle install
7
+
8
+ # Do any other automated setup that you need to do here
@@ -0,0 +1,6 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'pentest'
4
+ require 'pentest/commandline'
5
+
6
+ Pentest::Commandline.run
@@ -0,0 +1,77 @@
1
+ require "pentest/initializer"
2
+
3
+ require "pentest/version"
4
+ require "pentest/runner"
5
+ require "pentest/logger"
6
+ require "pentest/ruby_parser"
7
+ require "pentest/ast_utils"
8
+ require "pentest/checkers"
9
+ require "pentest/dsl"
10
+
11
+ module Pentest
12
+ class Error < StandardError; end
13
+
14
+ #Run Pentest scan. Returns Tracker object.
15
+ #
16
+ #Options:
17
+ #
18
+ # * :app_path - path to root of Rails app (required)
19
+ class << self
20
+ @@hooks = {before_attacks: [], setups: []}
21
+
22
+ def run options
23
+ Logger.debug "launched"
24
+
25
+ ENV['RAILS_ENV'] ||= 'test'
26
+
27
+ Logger.debug "Loading Rails project..."
28
+ @app_path = File.expand_path(options[:app_path])
29
+
30
+ # TODO: Check if app_path directory exists
31
+ # TODO: Check if app_path directory is valid rails project
32
+ # TODO: Detect rails version
33
+ require File.expand_path('config/environment', @app_path)
34
+
35
+ unless is_project_loaded?
36
+ # TODO: handle
37
+ end
38
+
39
+ Logger.debug "Loaded Rails project #{get_project_name.inspect}"
40
+
41
+ # TODO: Check if Pentestfile exists
42
+ pentestfile_path = options[:pentestfile] || 'Pentestfile'
43
+
44
+ Logger.debug "Loading #{pentestfile_path}..."
45
+ load_pentestfile(pentestfile_path)
46
+
47
+ Logger.debug "Initializing scanner..."
48
+ runner = Runner.new(@app_path, @@hooks)
49
+
50
+ runner.run
51
+ end
52
+
53
+ def is_project_loaded?
54
+ defined?(::Rails)
55
+ end
56
+
57
+ def get_project_name
58
+ if defined?(::Rails)
59
+ ::Rails.application.class.parent_name
60
+ end
61
+ end
62
+
63
+ def add_setup(*args, &block)
64
+ @@hooks[:setups] << block
65
+ end
66
+
67
+ def add_before_attack(*args, &block)
68
+ @@hooks[:before_attacks] << block
69
+ end
70
+
71
+ private
72
+
73
+ def load_pentestfile(pentestfile_path)
74
+ load(File.expand_path(pentestfile_path, @app_path))
75
+ end
76
+ end
77
+ end
@@ -0,0 +1,76 @@
1
+ require 'ruby_parser'
2
+
3
+ module Pentest
4
+ module AstUtils
5
+ class << self
6
+ # Match "params"
7
+ def is_params?(exp)
8
+ return false unless Sexp === exp
9
+
10
+ if exp[0] == :call
11
+ type, callee, method = exp
12
+ if callee.nil? && method == :params
13
+ true
14
+ else
15
+ false
16
+ end
17
+ end
18
+ end
19
+
20
+ # Match "params[:hoge]" and return :hoge
21
+ def get_params_key(exp)
22
+ return nil unless Sexp === exp
23
+
24
+ if exp[0] == :call
25
+ type, callee, method, arg = exp
26
+ if is_params?(callee) && method == :[]
27
+ if Sexp === arg && arg[0] == :lit
28
+ return arg[1]
29
+ end
30
+ if Sexp === arg && arg[0] == :str
31
+ return arg[1].to_sym
32
+ end
33
+ end
34
+ end
35
+
36
+ nil
37
+ end
38
+
39
+ def search_for_params(exp)
40
+ return Set.new unless Sexp === exp
41
+
42
+ ret = Set.new
43
+
44
+ params_key = get_params_key(exp)
45
+
46
+ unless params_key.nil?
47
+ ret << [params_key, nil, nil]
48
+ end
49
+
50
+ if exp[0] == :call
51
+ type, callee, method, arg = exp
52
+
53
+ callee_params = get_params_key(callee)
54
+ if callee_params.nil?
55
+ ret.merge search_for_params callee
56
+ else
57
+ ret << [callee_params, :callee, method, arg]
58
+ end
59
+
60
+ arg_params = get_params_key(arg)
61
+ if arg_params.nil?
62
+ ret.merge search_for_params arg
63
+ else
64
+ ret << [arg_params, :call_arg, callee, method]
65
+ end
66
+ else
67
+ exp.each do |child|
68
+ ret.merge search_for_params child
69
+ end
70
+ end
71
+
72
+ ret
73
+ end
74
+ end
75
+ end
76
+ end
@@ -0,0 +1,21 @@
1
+ module Pentest
2
+ class Checkers
3
+ @checkers = []
4
+
5
+ class << self
6
+ def add(checker)
7
+ @checkers << checker unless @checkers.include? checker
8
+ end
9
+
10
+ def run_checkers(endpoint, params)
11
+ @checkers.each do |checker_class|
12
+ checker = checker_class.new(endpoint, params)
13
+ yield(checker)
14
+ end
15
+ end
16
+ end
17
+ end
18
+ end
19
+
20
+ require 'pentest/checkers/sqli_checker'
21
+ require 'pentest/checkers/xss_checker'
@@ -0,0 +1,49 @@
1
+ class Pentest::BaseChecker
2
+ class << self
3
+ attr_reader :description
4
+ end
5
+
6
+ def initialize(endpoint, params)
7
+ @params = params
8
+ @warnings = []
9
+ @endpoint = endpoint
10
+ @route = endpoint.route
11
+ @app_path = endpoint.app_path
12
+ end
13
+
14
+ private
15
+
16
+ def dispatch(payload)
17
+ @endpoint.dispatch(payload)
18
+ end
19
+
20
+ def get_status(err)
21
+ if err.nil?
22
+ nil
23
+ elsif err.respond_to?(:status)
24
+ err.status
25
+ elsif ActiveRecord::RecordNotFound === err || ActionController::UrlGenerationError === err
26
+ 404
27
+ else
28
+ 500
29
+ end
30
+ end
31
+
32
+ def normalize_error(err, payload)
33
+ return if err.nil?
34
+
35
+ status = get_status(err)
36
+
37
+ return if status.nil? || status / 100 != 5
38
+
39
+ message = err.message.lines.first.strip
40
+ payload.params_hash.values.sort_by(&:size).reverse.each do |param|
41
+ message = message.gsub(param.inspect, '"[parameter]"')
42
+ if param.size >= 4
43
+ message = message.gsub(param, '[parameter]')
44
+ end
45
+ end
46
+
47
+ message
48
+ end
49
+ end