peplum-john 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 3557101f19534057d6928e39832552c6d3f752efc61ab5818f32dc12c4bf73fa
4
+ data.tar.gz: 9f52968910d916f5f29066a21d68afa0d12b9e0e1839145d77c907e4ab485437
5
+ SHA512:
6
+ metadata.gz: 3dea930e2f89973e7bd90830352d709db0274aceb90daad387760c6f3e83df2422f488ed262c0a22aeb76993fc6c24e0639e959a3fa11f6e8e52a382b5ca210c
7
+ data.tar.gz: 3bbf00ab6898ce84806a4dc92e082705ec1134ec32d656c4d7e2a861006cc86652a30074d8f38ede56680ac935f14cbd5cf26e2f1f5dbe1093e406e34ec38671
data/bin/console ADDED
@@ -0,0 +1,11 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ require "bundler/setup"
5
+ require "peplum/john"
6
+
7
+ # You can add fixtures and/or initialization code here to make experimenting
8
+ # with your gem easier. You can also use a different console, if you like.
9
+
10
+ require "irb"
11
+ IRB.start(__FILE__)
data/bin/setup ADDED
@@ -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,44 @@
1
+ require 'json'
2
+ require 'tmpdir'
3
+ require 'net/http'
4
+
5
+ def response
6
+ if @last_response['Content-Type'].include? 'json'
7
+ data = JSON.load( @last_response.body )
8
+ else
9
+ data = @last_response.body
10
+ end
11
+ {
12
+ code: @last_response.code,
13
+ data: data
14
+ }
15
+ end
16
+
17
+ def response_data
18
+ response[:data]
19
+ end
20
+
21
+ def request( method, resource = nil, parameters = nil )
22
+ uri = URI( "http://127.0.0.1:7331/#{resource}" )
23
+
24
+ Net::HTTP.start( uri.host, uri.port) do |http|
25
+ case method
26
+ when :get
27
+ uri.query = URI.encode_www_form( parameters ) if parameters
28
+ request = Net::HTTP::Get.new( uri )
29
+
30
+ when :post
31
+ request = Net::HTTP::Post.new( uri )
32
+ request.body = parameters.to_json
33
+
34
+ when :delete
35
+ request = Net::HTTP::Delete.new( uri )
36
+
37
+ when :put
38
+ request = Net::HTTP::Put.new( uri )
39
+ request.body = parameters.to_json
40
+ end
41
+
42
+ @last_response = http.request( request )
43
+ end
44
+ end
data/examples/rest.rb ADDED
@@ -0,0 +1,57 @@
1
+ require 'peplum/john'
2
+ require 'pp'
3
+ require_relative 'rest/helpers'
4
+
5
+ # Boot up our REST server for easy integration.
6
+ rest_pid = Peplum::John::Application.spawn( :rest, daemonize: true )
7
+ at_exit { Cuboid::Processes::Manager.kill rest_pid }
8
+
9
+ # Wait for the REST server to boot up.
10
+ while sleep 1
11
+ begin
12
+ request :get
13
+ rescue Errno::ECONNREFUSED
14
+ next
15
+ end
16
+
17
+ break
18
+ end
19
+
20
+ # Assign an Agent to the REST service for it to provide us with Instances.
21
+ john_agent = Peplum::John::Application.spawn( :agent, daemonize: true )
22
+ request :put, 'agent/url', john_agent.url
23
+ at_exit { john_agent.shutdown rescue nil }
24
+
25
+ # Create a new Instance and run with the following options.
26
+ request :post, 'instances', {
27
+ peplum: {
28
+ objects: %w(
29
+ 6ca13d52ca70c883e0f0bb101e425a89e8624de51db2d2392593af6a84118090
30
+ 36f583dd16f4e1e201eb1e6f6d8e35a2ccb3bbe2658de46b4ffae7b0e9ed872e
31
+ ),
32
+ max_workers: 2
33
+ },
34
+ payload: {
35
+ format: 'raw-sha256'
36
+ }
37
+ }
38
+
39
+ # The ID is used to represent that instance and allow us to manage it from here on out.
40
+ instance_id = response_data['id']
41
+
42
+ while sleep( 1 )
43
+ # Continue looping while instance status is 'busy'.
44
+ request :get, "instances/#{instance_id}"
45
+ break if !response_data['busy']
46
+ end
47
+
48
+ puts '*' * 88
49
+
50
+ # Get the report.
51
+ request :get, "instances/#{instance_id}/report.json"
52
+
53
+ # Print out the report.
54
+ puts JSON.pretty_generate( JSON.load( response_data['data'] ) )
55
+
56
+ # Shutdown the Instance.
57
+ request :delete, "instances/#{instance_id}"
data/examples/rpc.rb ADDED
@@ -0,0 +1,30 @@
1
+ require 'pp'
2
+ require 'peplum/john'
3
+
4
+ # Spawn an Agent as a daemon.
5
+ john_agent = Peplum::John::Application.spawn( :agent, daemonize: true )
6
+ at_exit { john_agent.shutdown rescue nil }
7
+
8
+ # Spawn and connect to an Instance.
9
+ john = Peplum::John::Application.connect( john_agent.spawn )
10
+ # Don't forget this!
11
+ at_exit { john.shutdown }
12
+
13
+ john.run(
14
+ peplum: {
15
+ objects: %w(
16
+ 6ca13d52ca70c883e0f0bb101e425a89e8624de51db2d2392593af6a84118090
17
+ 36f583dd16f4e1e201eb1e6f6d8e35a2ccb3bbe2658de46b4ffae7b0e9ed872e
18
+ ),
19
+ max_workers: 2
20
+ },
21
+ payload: {
22
+ format: 'raw-sha256'
23
+ }
24
+ )
25
+
26
+ # Waiting to complete.
27
+ sleep 1 while john.running?
28
+
29
+ # Hooray!
30
+ puts JSON.pretty_generate( john.generate_report.data )
@@ -0,0 +1,144 @@
1
+ require 'tmpdir'
2
+ require 'fileutils'
3
+
4
+ module Peplum
5
+ class John
6
+ class Application
7
+
8
+ module Payload
9
+
10
+ # For some reason doesn't work when specifying sane directories.
11
+ HASHES_FILE = "hashes.#{Process.pid}.txt"
12
+ at_exit { FileUtils.rm_f HASHES_FILE }
13
+
14
+ POT_FILE = "hashes.#{Process.pid}.pot"
15
+ at_exit { FileUtils.rm_f POT_FILE }
16
+
17
+ JOHN = 'john-the-ripper'
18
+
19
+ FORMATS = Set.new(%w(descrypt bsdicrypt md5crypt md5crypt-long bcrypt scrypt LM AFS
20
+ tripcode AndroidBackup adxcrypt agilekeychain aix-ssha1 aix-ssha256
21
+ aix-ssha512 andOTP ansible argon2 as400-des as400-ssha1 asa-md5
22
+ AxCrypt AzureAD BestCrypt BestCryptVE4 bfegg Bitcoin BitLocker
23
+ bitshares Bitwarden BKS Blackberry-ES10 WoWSRP Blockchain cardano
24
+ chap Clipperz cloudkeychain dynamic_n cq CRC32 cryptoSafe sha1crypt
25
+ sha256crypt sha512crypt Citrix_NS10 dahua dashlane diskcryptor Django
26
+ django-scrypt dmd5 dmg dominosec dominosec8 DPAPImk dragonfly3-32
27
+ dragonfly3-64 dragonfly4-32 dragonfly4-64 Drupal7 eCryptfs eigrp
28
+ electrum ENCDataVault-MD5 ENCDataVault-PBKDF2 EncFS enpass EPI
29
+ EPiServer ethereum fde Fortigate256 Fortigate FormSpring FVDE geli
30
+ gost gpg HAVAL-128-4 HAVAL-256-3 hdaa hMailServer hsrp IKE ipb2
31
+ itunes-backup iwork KeePass keychain keyring keystore known_hosts
32
+ krb4 krb5 krb5asrep krb5pa-sha1 krb5pa-md5 krb5tgs krb5-17 krb5-18
33
+ krb5-3 kwallet lp lpcli leet lotus5 lotus85 LUKS MD2 mdc2
34
+ MediaWiki monero money MongoDB scram Mozilla mscash mscash2 MSCHAPv2
35
+ mschapv2-naive mssql mssql05 mssql12 multibit mysqlna mysql-sha1
36
+ mysql net-ah nethalflm netlm netlmv2 net-md5 netntlmv2 netntlm
37
+ netntlm-naive net-sha1 nk notes md5ns nsec3 NT NT-long o10glogon
38
+ o3logon o5logon ODF Office oldoffice OpenBSD-SoftRAID openssl-enc
39
+ oracle oracle11 Oracle12C osc ospf Padlock Palshop Panama
40
+ PBKDF2-HMAC-MD4 PBKDF2-HMAC-MD5 PBKDF2-HMAC-SHA1 PBKDF2-HMAC-SHA256
41
+ PBKDF2-HMAC-SHA512 PDF PEM pfx pgpdisk pgpsda pgpwde phpass PHPS
42
+ PHPS2 pix-md5 PKZIP po postgres PST PuTTY pwsafe qnx RACF
43
+ RACF-KDFAES radius RAdmin RAKP rar RAR5 Raw-SHA512 Raw-Blake2
44
+ Raw-Keccak Raw-Keccak-256 Raw-MD4 Raw-MD5 Raw-MD5u Raw-SHA1
45
+ Raw-SHA1-AxCrypt Raw-SHA1-Linkedin Raw-SHA224 Raw-SHA256 Raw-SHA3
46
+ Raw-SHA384 restic ripemd-128 ripemd-160 rsvp RVARY Siemens-S7
47
+ Salted-SHA1 SSHA512 sapb sapg saph sappse securezip 7z Signal SIP
48
+ skein-256 skein-512 skey SL3 Snefru-128 Snefru-256 LastPass SNMP
49
+ solarwinds SSH sspr Stribog-256 Stribog-512 STRIP SunMD5 SybaseASE
50
+ Sybase-PROP tacacs-plus tcp-md5 telegram tezos Tiger timeroast
51
+ tc_aes_xts tc_ripemd160 tc_ripemd160boot tc_sha512 tc_whirlpool vdi
52
+ OpenVMS vmx VNC vtp wbb3 whirlpool whirlpool0 whirlpool1 wpapsk
53
+ wpapsk-pmk xmpp-scram xsha xsha512 zed ZIP ZipMonster plaintext
54
+ has-160 HMAC-MD5 HMAC-SHA1 HMAC-SHA224 HMAC-SHA256 HMAC-SHA384
55
+ HMAC-SHA512 AndroidBackup-opencl agilekeychain-opencl ansible-opencl
56
+ axcrypt-opencl axcrypt2-opencl bcrypt-opencl Bitcoin-opencl
57
+ BitLocker-opencl bitwarden-opencl blockchain-opencl cloudkeychain-opencl
58
+ md5crypt-opencl cryptosafe-opencl sha1crypt-opencl sha256crypt-opencl
59
+ sha512crypt-opencl dashlane-opencl descrypt-opencl diskcryptor-opencl
60
+ diskcryptor-aes-opencl dmg-opencl electrum-modern-opencl EncFS-opencl
61
+ enpass-opencl ethereum-opencl ethereum-presale-opencl FVDE-opencl
62
+ geli-opencl gpg-opencl iwork-opencl KeePass-opencl keychain-opencl
63
+ keyring-opencl keystore-opencl krb5pa-md5-opencl krb5pa-sha1-opencl
64
+ krb5tgs-opencl krb5asrep-aes-opencl lp-opencl lpcli-opencl LM-opencl
65
+ lotus5-opencl mscash-opencl mscash2-opencl mysql-sha1-opencl
66
+ notes-opencl NT-opencl ntlmv2-opencl NT-long-opencl o5logon-opencl
67
+ ODF-opencl office-opencl oldoffice-opencl OpenBSD-SoftRAID-opencl
68
+ PBKDF2-HMAC-SHA256-opencl PBKDF2-HMAC-SHA512-opencl PBKDF2-HMAC-MD4-opencl
69
+ PBKDF2-HMAC-MD5-opencl PBKDF2-HMAC-SHA1-opencl pem-opencl pfx-opencl
70
+ pgpdisk-opencl pgpsda-opencl pgpwde-opencl phpass-opencl pwsafe-opencl
71
+ RAKP-opencl rar-opencl RAR5-opencl raw-MD4-opencl raw-MD5-opencl
72
+ raw-SHA1-opencl raw-SHA256-opencl raw-SHA512-free-opencl
73
+ raw-SHA512-opencl salted-SHA1-opencl sappse-opencl 7z-opencl SL3-opencl
74
+ solarwinds-opencl ssh-opencl sspr-opencl strip-opencl TrueCrypt-opencl
75
+ telegram-opencl tezos-opencl timeroast-opencl vmx-opencl wpapsk-opencl
76
+ wpapsk-pmk-opencl XSHA512-free-opencl XSHA512-opencl zed-opencl
77
+ ))
78
+
79
+ def run( hashes, options )
80
+ validate( options )
81
+
82
+ File.open( HASHES_FILE, 'w+', 0666 ) do |f|
83
+ hashes.each do |hash|
84
+ f.puts hash
85
+ end
86
+ end
87
+
88
+ _run options
89
+ end
90
+
91
+ # Distribute `objects` into `chunks` amount of groups, one for each worker.
92
+ #
93
+ # @param [Array] objects All objects that need to be processed.
94
+ # @param [Integer] chunks Amount of object groups that should be generated.
95
+ #
96
+ # @return [Array<Array<Object>>] `objects` split in `chunks` amount of groups
97
+ # @abstract
98
+ def group( objects, chunks )
99
+ objects.chunk chunks
100
+ end
101
+
102
+ # Merge result `data` for reporting.
103
+ #
104
+ # @param [Array] data Report data from workers.
105
+ # @abstract
106
+ def merge( data )
107
+ f = data.pop
108
+ data.each { |d| f.merge! d }
109
+ f
110
+ end
111
+
112
+ private
113
+
114
+ def executable
115
+ @executable ||= `which #{JOHN}`.strip
116
+ return @executable if !@executable.empty?
117
+
118
+ fail Error, 'Could not locate John The Ripper executable!'
119
+ end
120
+
121
+ def _run( options )
122
+ `#{executable} --no-log --pot=#{POT_FILE} --format=#{options['format']} #{HASHES_FILE} 2> /dev/null`
123
+ `#{executable} --format=#{options['format']} #{HASHES_FILE} 2> /dev/null`
124
+
125
+ results = {}
126
+ File.open( POT_FILE , 'r' ) do |f|
127
+ line = f.readline
128
+ hash, password = line.split( '$' ).last.split( ':' )
129
+ results[hash] = password.strip
130
+ end
131
+ results
132
+ end
133
+
134
+ def validate( options )
135
+ fail ArgumentError, 'Missing hash format' if !options['format']
136
+ fail ArgumentError, "Unknown format: options['format']" if FORMATS.include? options['format']
137
+ end
138
+
139
+ extend self
140
+ end
141
+
142
+ end
143
+ end
144
+ end
@@ -0,0 +1,21 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'peplum'
4
+
5
+ module Peplum
6
+ class John
7
+
8
+ class Application < Peplum::Application
9
+ require_relative "application/payload"
10
+
11
+ provision_memory 100 * 1024 * 1024
12
+ provision_disk 100 * 1024 * 1024
13
+
14
+ def payload
15
+ Payload
16
+ end
17
+
18
+ end
19
+
20
+ end
21
+ end
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Peplum
4
+ class John
5
+ VERSION = "0.2.0"
6
+ end
7
+ end
@@ -0,0 +1,15 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'peplum'
4
+
5
+ module Peplum
6
+ class John
7
+
8
+ require_relative "john/version"
9
+
10
+ class Error < Peplum::Error; end
11
+
12
+ require_relative "john/application"
13
+
14
+ end
15
+ end
@@ -0,0 +1,23 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "lib/peplum/john/version"
4
+
5
+ Gem::Specification.new do |spec|
6
+ spec.name = "peplum-john"
7
+ spec.version = Peplum::John::VERSION
8
+ spec.authors = ["Tasos Laskos"]
9
+ spec.email = ["tasos.laskos@ecsypno.com"]
10
+
11
+ spec.summary = "Peplum-powered John the Ripper."
12
+ spec.description = "A distributed approach to the John the Ripper password recovery tool"
13
+ spec.homepage = "http://ecsypno.com/"
14
+ spec.required_ruby_version = ">= 2.6.0"
15
+
16
+ spec.files = Dir.glob( 'bin/*')
17
+ spec.files += Dir.glob( 'lib/**/*')
18
+ spec.files += Dir.glob( 'examples/**/*')
19
+ spec.files += %w(peplum-john.gemspec)
20
+
21
+
22
+ spec.add_dependency "peplum"
23
+ end
metadata ADDED
@@ -0,0 +1,66 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: peplum-john
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.2.0
5
+ platform: ruby
6
+ authors:
7
+ - Tasos Laskos
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2023-05-24 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: peplum
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ description: A distributed approach to the John the Ripper password recovery tool
28
+ email:
29
+ - tasos.laskos@ecsypno.com
30
+ executables: []
31
+ extensions: []
32
+ extra_rdoc_files: []
33
+ files:
34
+ - bin/console
35
+ - bin/setup
36
+ - examples/rest.rb
37
+ - examples/rest/helpers.rb
38
+ - examples/rpc.rb
39
+ - lib/peplum/john.rb
40
+ - lib/peplum/john/application.rb
41
+ - lib/peplum/john/application/payload.rb
42
+ - lib/peplum/john/version.rb
43
+ - peplum-john.gemspec
44
+ homepage: http://ecsypno.com/
45
+ licenses: []
46
+ metadata: {}
47
+ post_install_message:
48
+ rdoc_options: []
49
+ require_paths:
50
+ - lib
51
+ required_ruby_version: !ruby/object:Gem::Requirement
52
+ requirements:
53
+ - - ">="
54
+ - !ruby/object:Gem::Version
55
+ version: 2.6.0
56
+ required_rubygems_version: !ruby/object:Gem::Requirement
57
+ requirements:
58
+ - - ">="
59
+ - !ruby/object:Gem::Version
60
+ version: '0'
61
+ requirements: []
62
+ rubygems_version: 3.4.13
63
+ signing_key:
64
+ specification_version: 4
65
+ summary: Peplum-powered John the Ripper.
66
+ test_files: []