yawast 0.7.0.beta1 → 0.7.0.beta2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (50) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +12 -0
  3. data/CHANGELOG.md +5 -1
  4. data/Gemfile +2 -2
  5. data/README.md +8 -1
  6. data/Rakefile +1 -1
  7. data/bin/yawast +8 -0
  8. data/lib/commands/cms.rb +2 -0
  9. data/lib/commands/dns.rb +3 -3
  10. data/lib/commands/head.rb +2 -0
  11. data/lib/commands/scan.rb +2 -0
  12. data/lib/commands/ssl.rb +2 -0
  13. data/lib/commands/utils.rb +5 -3
  14. data/lib/scanner/core.rb +34 -26
  15. data/lib/scanner/generic.rb +33 -130
  16. data/lib/scanner/plugins/applications/cms/generic.rb +20 -0
  17. data/lib/scanner/plugins/applications/generic/password_reset.rb +180 -0
  18. data/lib/scanner/plugins/dns/caa.rb +30 -12
  19. data/lib/scanner/plugins/dns/generic.rb +38 -1
  20. data/lib/scanner/plugins/http/directory_search.rb +14 -12
  21. data/lib/scanner/plugins/http/file_presence.rb +21 -13
  22. data/lib/scanner/plugins/http/generic.rb +95 -0
  23. data/lib/scanner/plugins/servers/apache.rb +23 -23
  24. data/lib/scanner/plugins/servers/generic.rb +25 -0
  25. data/lib/scanner/plugins/servers/iis.rb +6 -6
  26. data/lib/scanner/plugins/servers/nginx.rb +3 -1
  27. data/lib/scanner/plugins/servers/python.rb +3 -1
  28. data/lib/scanner/plugins/spider/spider.rb +7 -7
  29. data/lib/scanner/plugins/ssl/ssl.rb +14 -14
  30. data/lib/scanner/plugins/ssl/ssl_labs/analyze.rb +14 -13
  31. data/lib/scanner/plugins/ssl/ssl_labs/info.rb +6 -4
  32. data/lib/scanner/plugins/ssl/sweet32.rb +68 -63
  33. data/lib/scanner/ssl.rb +33 -36
  34. data/lib/scanner/ssl_labs.rb +373 -110
  35. data/lib/scanner/vuln_scan.rb +27 -0
  36. data/lib/shared/http.rb +31 -27
  37. data/lib/shared/output.rb +7 -15
  38. data/lib/shared/uri.rb +14 -14
  39. data/lib/string_ext.rb +10 -4
  40. data/lib/uri_ext.rb +1 -1
  41. data/lib/util.rb +28 -0
  42. data/lib/version.rb +3 -1
  43. data/lib/yawast.rb +12 -2
  44. data/test/data/ssl_labs_analyze_data_cam_hmhreservations_com.json +1933 -0
  45. data/test/test_scan_cms.rb +2 -2
  46. data/test/test_ssl_labs_analyze.rb +15 -0
  47. data/yawast.gemspec +8 -5
  48. metadata +75 -28
  49. data/lib/scanner/cms.rb +0 -14
  50. data/lib/scanner/php.rb +0 -19
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'date'
2
4
  require 'openssl'
3
5
  require 'digest/sha1'
@@ -10,7 +12,7 @@ module Yawast
10
12
  puts 'Beginning SSL Labs scan (this could take a minute or two)'
11
13
 
12
14
  begin
13
- endpoint = URI::Parser.new.parse 'https://api.ssllabs.com'
15
+ endpoint = URI::DEFAULT_PARSER.parse 'https://api.ssllabs.com'
14
16
 
15
17
  info_body = Yawast::Scanner::Plugins::SSL::SSLLabs::Info.call_info endpoint
16
18
 
@@ -39,12 +41,12 @@ module Yawast
39
41
  json = nil
40
42
  begin
41
43
  json = JSON.parse data_body
42
- rescue => e
44
+ rescue => e # rubocop:disable Style/RescueStandardError
43
45
  raise Exception, "Invalid response from SSL Labs: '#{e.message}'"
44
46
  end
45
47
 
46
48
  process_results uri, json, tdes_session_count
47
- rescue => e
49
+ rescue => e # rubocop:disable Style/RescueStandardError
48
50
  puts
49
51
  Yawast::Utilities.puts_error "SSL Labs Error: #{e.message}"
50
52
  end
@@ -65,7 +67,7 @@ module Yawast
65
67
  else
66
68
  Yawast::Utilities.puts_error "Error getting information for IP: #{ep['ipAddress']}: #{ep['statusMessage']}"
67
69
  end
68
- rescue => e
70
+ rescue => e # rubocop:disable Style/RescueStandardError
69
71
  Yawast::Utilities.puts_error "Error getting information for IP: #{ep['ipAddress']}: #{e.message}"
70
72
  end
71
73
 
@@ -76,13 +78,13 @@ module Yawast
76
78
  else
77
79
  Yawast::Utilities.puts_error 'SSL Labs Error: No Endpoint Data Received.'
78
80
 
79
- #TODO - Remove this before release
81
+ # TODO: Remove this before release
80
82
  puts
81
83
  puts "DEBUG DATA (send to adam@adamcaudill.com): #{body}"
82
84
  puts
83
85
  puts
84
86
  end
85
- rescue => e
87
+ rescue => e # rubocop:disable Style/RescueStandardError
86
88
  puts
87
89
  Yawast::Utilities.puts_error "SSL Labs Error: #{e.message}"
88
90
  end
@@ -100,44 +102,26 @@ module Yawast
100
102
  end
101
103
 
102
104
  puts "\tCertificate Information:"
103
- unless cert['issues'] == 0
105
+ unless cert['issues'].zero?
104
106
  Yawast::Utilities.puts_vuln "\t\tCertificate Has Issues - Not Valid"
105
107
 
106
- if cert['issues'] & 1 != 0
107
- Yawast::Utilities.puts_vuln "\t\tCertificate Issue: no chain of trust"
108
- end
108
+ Yawast::Utilities.puts_vuln "\t\tCertificate Issue: no chain of trust" if cert['issues'] & 1 != 0
109
109
 
110
- if cert['issues'] & (1<<1) != 0
111
- Yawast::Utilities.puts_vuln "\t\tCertificate Issue: certificate not yet valid"
112
- end
110
+ Yawast::Utilities.puts_vuln "\t\tCertificate Issue: certificate not yet valid" if cert['issues'] & (1 << 1) != 0
113
111
 
114
- if cert['issues'] & (1<<2) != 0
115
- Yawast::Utilities.puts_vuln "\t\tCertificate Issue: certificate expired"
116
- end
112
+ Yawast::Utilities.puts_vuln "\t\tCertificate Issue: certificate expired" if cert['issues'] & (1 << 2) != 0
117
113
 
118
- if cert['issues'] & (1<<3) != 0
119
- Yawast::Utilities.puts_vuln "\t\tCertificate Issue: hostname mismatch"
120
- end
114
+ Yawast::Utilities.puts_vuln "\t\tCertificate Issue: hostname mismatch" if cert['issues'] & (1 << 3) != 0
121
115
 
122
- if cert['issues'] & (1<<4) != 0
123
- Yawast::Utilities.puts_vuln "\t\tCertificate Issue: revoked"
124
- end
116
+ Yawast::Utilities.puts_vuln "\t\tCertificate Issue: revoked" if cert['issues'] & (1 << 4) != 0
125
117
 
126
- if cert['issues'] & (1<<5) != 0
127
- Yawast::Utilities.puts_vuln "\t\tCertificate Issue: bad common name"
128
- end
118
+ Yawast::Utilities.puts_vuln "\t\tCertificate Issue: bad common name" if cert['issues'] & (1 << 5) != 0
129
119
 
130
- if cert['issues'] & (1<<6) != 0
131
- Yawast::Utilities.puts_vuln "\t\tCertificate Issue: self-signed"
132
- end
120
+ Yawast::Utilities.puts_vuln "\t\tCertificate Issue: self-signed" if cert['issues'] & (1 << 6) != 0
133
121
 
134
- if cert['issues'] & (1<<7) != 0
135
- Yawast::Utilities.puts_vuln "\t\tCertificate Issue: blacklisted"
136
- end
122
+ Yawast::Utilities.puts_vuln "\t\tCertificate Issue: blacklisted" if cert['issues'] & (1 << 7) != 0
137
123
 
138
- if cert['issues'] & (1<<8) != 0
139
- Yawast::Utilities.puts_vuln "\t\tCertificate Issue: insecure signature"
140
- end
124
+ Yawast::Utilities.puts_vuln "\t\tCertificate Issue: insecure signature" if cert['issues'] & (1 << 8) != 0
141
125
  end
142
126
 
143
127
  Yawast::Utilities.puts_info "\t\tSubject: #{cert['subject']}"
@@ -166,17 +150,56 @@ module Yawast
166
150
 
167
151
  Yawast::Utilities.puts_info "\t\tVersion: #{ossl_cert.version}"
168
152
 
169
- Yawast::Utilities.puts_info "\t\tSerial: #{ossl_cert.serial}"
153
+ serial = format('%02x', ossl_cert.serial.to_i)
154
+ serial = "0#{serial}" unless serial.length.even?
155
+ Yawast::Utilities.puts_info "\t\tSerial: #{serial}"
156
+
157
+ ## if the serial is exactly 16 hex digits, it may have an entropy issue.
158
+ if serial.length == 16
159
+ puts
160
+
161
+ Yawast::Utilities.puts_warn "\t\tSerial number is exactly 64 bits. Serial may not comply with CA/B Forum requirements."
162
+ Yawast::Utilities.puts_raw "\t\t\t See https://adamcaudill.com/2019/03/09/tls-64bit-ish-serial-numbers-mass-revocation/ for details."
163
+
164
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
165
+ 'tls_serial_exactly_64_bits',
166
+ {vulnerable: true, length: (serial.length / 2) * 8}
167
+
168
+ puts
169
+ elsif serial.length < 16
170
+ puts
171
+
172
+ Yawast::Utilities.puts_vuln "\t\tSerial number is less than 64 bits. Serial does not comply with CA/B Forum requirements."
173
+
174
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
175
+ 'tls_serial_less_than_64_bits',
176
+ {vulnerable: true, length: (serial.length / 2) * 8}
177
+
178
+ puts
179
+ else
180
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
181
+ 'tls_serial_exactly_64_bits',
182
+ {vulnerable: false, length: (serial.length / 2) * 8}
183
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
184
+ 'tls_serial_less_than_64_bits',
185
+ {vulnerable: false, length: (serial.length / 2) * 8}
186
+ end
170
187
 
171
188
  Yawast::Utilities.puts_info "\t\tIssuer: #{cert['issuerSubject']}"
172
189
 
173
190
  if cert['sigAlg'].include?('SHA1') || cert['sigAlg'].include?('MD5')
174
191
  Yawast::Utilities.puts_vuln "\t\tSignature algorithm: #{cert['sigAlg']}"
192
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
193
+ 'tls_weak_sig_alg',
194
+ {vulnerable: true, algorithm: cert['sigAlg']}
175
195
  else
176
196
  Yawast::Utilities.puts_info "\t\tSignature algorithm: #{cert['sigAlg']}"
197
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
198
+ 'tls_weak_sig_alg',
199
+ {vulnerable: false, algorithm: cert['sigAlg']}
177
200
  end
178
201
 
179
- #todo - figure out what the options for this value are
202
+ # TODO: figure out what the options for this value are
180
203
  if cert['validationType'] == 'E'
181
204
  Yawast::Utilities.puts_info "\t\tExtended Validation: Yes"
182
205
  elsif cert['validationType'] == 'D'
@@ -192,12 +215,12 @@ module Yawast
192
215
  end
193
216
 
194
217
  # check second bit, SCT in stapled OSCP response
195
- if ep['details']['hasSct'] & (1<<1) != 0
218
+ if ep['details']['hasSct'] & (1 << 1) != 0
196
219
  Yawast::Utilities.puts_info "\t\tCertificate Transparency: SCT in the stapled OCSP response"
197
220
  end
198
221
 
199
222
  # check third bit, SCT in the TLS extension
200
- if ep['details']['hasSct'] & (1<<2) != 0
223
+ if ep['details']['hasSct'] & (1 << 2) != 0
201
224
  Yawast::Utilities.puts_info "\t\tCertificate Transparency: SCT in the TLS extension (ServerHello)"
202
225
  end
203
226
  else
@@ -209,7 +232,7 @@ module Yawast
209
232
  if cert['revocationInfo'] & 1 != 0
210
233
  Yawast::Utilities.puts_info "\t\tRevocation information: CRL information available"
211
234
  end
212
- if cert['revocationInfo'] & (1<<1) != 0
235
+ if cert['revocationInfo'] & (1 << 1) != 0
213
236
  Yawast::Utilities.puts_info "\t\tRevocation information: OCSP information available"
214
237
  end
215
238
 
@@ -244,18 +267,18 @@ module Yawast
244
267
  path_count = 0
245
268
 
246
269
  # build list of trust paths
247
- trust_paths = Hash.new
270
+ trust_paths = {}
248
271
  chain['trustPaths'].each do |path|
249
272
  trusts = nil
250
273
  # in practice, it seems there is only only per path, but just in case
251
274
  path['trust'].each do |trust|
252
- if trust['isTrusted']
253
- trust_line = "#{trust['rootStore']} (trusted)"
254
- else
255
- trust_line = "#{trust['rootStore']} (#{trust['trustErrorMessage']})"
256
- end
275
+ trust_line = if trust['isTrusted']
276
+ "#{trust['rootStore']} (trusted)"
277
+ else
278
+ "#{trust['rootStore']} (#{trust['trustErrorMessage']})"
279
+ end
257
280
 
258
- if trusts == nil
281
+ if trusts.nil?
259
282
  trusts = trust_line
260
283
  else
261
284
  trusts += " #{trust_line}"
@@ -277,25 +300,31 @@ module Yawast
277
300
  puts "\t\t Root Stores: #{trust_paths[key]}"
278
301
 
279
302
  # cert chain issues
280
- if chain['issues'] & (1<<1) != 0
303
+ if chain['issues'] & (1 << 1) != 0
281
304
  Yawast::Utilities.puts_warn "\t\tCertificate Chain Issue: incomplete chain"
305
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
306
+ 'tls_chain_incomplete',
307
+ {vulnerable: true}
308
+ else
309
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
310
+ 'tls_chain_incomplete',
311
+ {vulnerable: false}
282
312
  end
283
313
 
284
- if chain['issues'] & (1<<2) != 0
314
+ if chain['issues'] & (1 << 2) != 0
285
315
  Yawast::Utilities.puts_warn "\t\tCertificate Chain Issue: chain contains unrelated/duplicate certificates"
286
316
  end
287
317
 
288
- if chain['issues'] & (1<<3) != 0
289
- Yawast::Utilities.puts_warn "\t\tCertificate Chain Issue: incorrect order"
290
- end
318
+ Yawast::Utilities.puts_warn "\t\tCertificate Chain Issue: incorrect order" if chain['issues'] & (1 << 3) != 0
291
319
 
292
- if chain['issues'] & (1<<4) != 0
293
- Yawast::Utilities.puts_warn "\t\tCertificate Chain Issue: contains anchor"
294
- end
320
+ Yawast::Utilities.puts_warn "\t\tCertificate Chain Issue: contains anchor" if chain['issues'] & (1 << 4) != 0
295
321
 
296
- if cert['issues'] & (1<<5) != 0
297
- Yawast::Utilities.puts_warn "\t\tCertificate Chain Issue: untrusted"
298
- end
322
+ Yawast::Utilities.puts_warn "\t\tCertificate Chain Issue: untrusted" if cert['issues'] & (1 << 5) != 0
323
+
324
+ # setup the log entry for a symantec root - this will overwrite if one is found
325
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
326
+ 'tls_symantec_root',
327
+ {vulnerable: false, root_hash: ''}
299
328
 
300
329
  key.each do |path_cert|
301
330
  body['certs'].each do |c|
@@ -305,11 +334,14 @@ module Yawast
305
334
 
306
335
  if Yawast::Scanner::Plugins::SSL::SSL.check_symantec_root(c['sha256Hash'])
307
336
  Yawast::Utilities.puts_vuln "\t\t\t Untrusted Symantec Root"
337
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
338
+ 'tls_symantec_root',
339
+ {vulnerable: true, :root_hash => c['sha256Hash']}
308
340
  end
309
341
 
310
342
  Yawast::Utilities.puts_info "\t\t\t https://crt.sh/?q=#{c['sha1Hash']}"
311
343
 
312
- if chain['certIds'].find_index(c['sha256Hash']) != nil
344
+ unless chain['certIds'].find_index(c['sha256Hash']).nil?
313
345
  Yawast::Utilities.puts_info "\t\t\t (provided by server)"
314
346
  end
315
347
 
@@ -327,24 +359,53 @@ module Yawast
327
359
  puts "\tConfiguration Information:"
328
360
 
329
361
  puts "\t\tProtocol Support:"
330
- protos = Hash.new
362
+ # setup JSON output
363
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
364
+ 'tls_legacy_ssl',
365
+ {vulnerable: false}
366
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
367
+ 'tls_tls10_enabled',
368
+ {vulnerable: false}
369
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
370
+ 'tls_tls13_not_enabled',
371
+ {vulnerable: true}
372
+
373
+ # check protocols
374
+ protos = {}
375
+ tls13_enabled = false
331
376
  ep['details']['protocols'].each do |proto|
332
377
  if proto['name'] == 'SSL'
333
378
  # show a vuln for SSLvX
334
379
  Yawast::Utilities.puts_vuln "\t\t\t#{proto['name']} #{proto['version']}"
380
+
381
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
382
+ 'tls_legacy_ssl',
383
+ {vulnerable: true}
335
384
  elsif proto['name'] == 'TLS' && proto['version'] == '1.0'
336
385
  # show a warn for TLSv1.0
337
386
  Yawast::Utilities.puts_warn "\t\t\t#{proto['name']} #{proto['version']}"
387
+
388
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
389
+ 'tls_tls10_enabled',
390
+ {vulnerable: true}
391
+ elsif proto['name'] == 'TLS' && proto['version'] == '1.3'
392
+ # capture TLS 1.3 status
393
+ tls13_enabled = true
394
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
395
+ 'tls_tls13_not_enabled',
396
+ {vulnerable: false}
338
397
  else
339
398
  Yawast::Utilities.puts_info "\t\t\t#{proto['name']} #{proto['version']}"
340
399
  end
341
400
 
342
401
  protos[proto['id']] = "#{proto['name']} #{proto['version']}"
343
402
  end
403
+
404
+ Yawast::Utilities.puts_warn "\t\t\tTLS 1.3 Is Not Enabled" unless tls13_enabled
344
405
  puts
345
406
 
346
407
  puts "\t\tNamed Group Support:"
347
- if ep['details']['namedGroups'] != nil
408
+ unless ep['details']['namedGroups'].nil?
348
409
  ep['details']['namedGroups']['list'].each do |group|
349
410
  Yawast::Utilities.puts_info "\t\t\t#{group['name']} #{group['bits']}"
350
411
  end
@@ -352,7 +413,21 @@ module Yawast
352
413
  end
353
414
 
354
415
  puts "\t\tCipher Suite Support:"
355
- if ep['details']['suites'] != nil
416
+ # setup JSON output
417
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
418
+ 'tls_insecure_cipher_suites',
419
+ {vulnerable: false}
420
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
421
+ 'tls_weak_cipher_suites',
422
+ {vulnerable: false}
423
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
424
+ 'tls_3des_enabled',
425
+ {vulnerable: false, suite: ''}
426
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
427
+ 'tls_rc4_enabled',
428
+ {vulnerable: false, suite: ''}
429
+
430
+ if !ep['details']['suites'].nil?
356
431
  ep['details']['suites'].each do |proto_suites|
357
432
  Yawast::Utilities.puts_info "\t\t\t#{protos[proto_suites['protocol']]}"
358
433
 
@@ -364,22 +439,40 @@ module Yawast
364
439
  # in this case, the effective strength is only 112 bits,
365
440
  # which is what we want to report. So override SSL Labs
366
441
  strength = 112
442
+
443
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
444
+ 'tls_3des_enabled',
445
+ {vulnerable: true, suite: suite['name']}
367
446
  end
368
447
 
369
- if ke != nil
370
- suite_info = "#{suite['name'].ljust(50)} - #{strength}-bits - #{ke}"
371
- else
372
- suite_info = "#{suite['name'].ljust(50)} - #{strength}-bits"
448
+ if suite['name'].include? 'RC4'
449
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
450
+ 'tls_rc4_enabled',
451
+ {vulnerable: true, suite: suite['name']}
373
452
  end
374
453
 
454
+ suite_info = if !ke.nil?
455
+ "#{suite['name'].ljust(50)} - #{strength}-bits - #{ke}"
456
+ else
457
+ "#{suite['name'].ljust(50)} - #{strength}-bits"
458
+ end
459
+
375
460
  if cipher_suite_secure? suite
376
461
  if strength >= 128
377
462
  Yawast::Utilities.puts_info "\t\t\t #{suite_info}"
378
463
  else
379
464
  Yawast::Utilities.puts_warn "\t\t\t #{suite_info}"
465
+
466
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
467
+ 'tls_weak_cipher_suites',
468
+ {vulnerable: true}
380
469
  end
381
470
  else
382
471
  Yawast::Utilities.puts_vuln "\t\t\t #{suite_info}"
472
+
473
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
474
+ 'tls_insecure_cipher_suites',
475
+ {vulnerable: true}
383
476
  end
384
477
  end
385
478
  end
@@ -390,15 +483,13 @@ module Yawast
390
483
  puts
391
484
 
392
485
  puts "\t\tHandshake Simulation:"
393
- if ep['details']['sims']['results'] != nil
486
+ if !ep['details']['sims']['results'].nil?
394
487
  ep['details']['sims']['results'].each do |sim|
395
488
  name = "#{sim['client']['name']} #{sim['client']['version']}"
396
- if sim['client']['platform'] != nil
397
- name += " / #{sim['client']['platform']}"
398
- end
489
+ name += " / #{sim['client']['platform']}" unless sim['client']['platform'].nil?
399
490
  name = name.ljust(28)
400
491
 
401
- if sim['errorCode'] == 0
492
+ if sim['errorCode'].zero?
402
493
  protocol = protos[sim['protocolId']]
403
494
 
404
495
  ke = get_key_exchange sim
@@ -427,29 +518,50 @@ module Yawast
427
518
  Yawast::Utilities.puts_vuln "\t\t\t\t#{dh['ip']}:#{dh['port']} - #{dh['status']}"
428
519
  puts "\t\t\t\thttps://test.drownattack.com/?site=#{dh['ip']}"
429
520
  end
521
+
522
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
523
+ 'tls_drown',
524
+ {vulnerable: true}
430
525
  else
431
526
  Yawast::Utilities.puts_info "\t\t\tDROWN: No"
432
- end
433
527
 
434
- if ep['details']['renegSupport'] & 1 != 0
435
- Yawast::Utilities.puts_vuln "\t\t\tSecure Renegotiation: insecure client-initiated renegotiation supported"
436
- end
437
- if ep['details']['renegSupport'] & (1<<1) != 0
438
- Yawast::Utilities.puts_info "\t\t\tSecure Renegotiation: secure renegotiation supported"
528
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
529
+ 'tls_drown',
530
+ {vulnerable: false}
439
531
  end
440
- if ep['details']['renegSupport'] & (1<<2) != 0
441
- Yawast::Utilities.puts_info "\t\t\tSecure Renegotiation: secure client-initiated renegotiation supported"
442
- end
443
- if ep['details']['renegSupport'] & (1<<3) != 0
444
- Yawast::Utilities.puts_info "\t\t\tSecure Renegotiation: server requires secure renegotiation support"
532
+
533
+ unless ep['details']['renegSupport'].nil?
534
+ if ep['details']['renegSupport'] & 1 != 0
535
+ Yawast::Utilities.puts_vuln "\t\t\tSecure Renegotiation: insecure client-initiated renegotiation supported"
536
+ end
537
+ if ep['details']['renegSupport'] & (1 << 1) != 0
538
+ Yawast::Utilities.puts_info "\t\t\tSecure Renegotiation: secure renegotiation supported"
539
+ end
540
+ if ep['details']['renegSupport'] & (1 << 2) != 0
541
+ Yawast::Utilities.puts_info "\t\t\tSecure Renegotiation: secure client-initiated renegotiation supported"
542
+ end
543
+ if ep['details']['renegSupport'] & (1 << 3) != 0
544
+ Yawast::Utilities.puts_info "\t\t\tSecure Renegotiation: server requires secure renegotiation support"
545
+ end
445
546
  end
446
547
 
447
548
  if ep['details']['poodle']
448
549
  Yawast::Utilities.puts_vuln "\t\t\tPOODLE (SSL): Vulnerable"
550
+
551
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
552
+ 'tls_poodle_ssl',
553
+ {vulnerable: true}
449
554
  else
450
555
  Yawast::Utilities.puts_info "\t\t\tPOODLE (SSL): No"
556
+
557
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
558
+ 'tls_poodle_ssl',
559
+ {vulnerable: false}
451
560
  end
452
561
 
562
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
563
+ 'tls_poodle',
564
+ {vulnerable: false}
453
565
  case ep['details']['poodleTls']
454
566
  when -3
455
567
  Yawast::Utilities.puts_info "\t\t\tPOODLE (TLS): Inconclusive (Timeout)"
@@ -463,34 +575,72 @@ module Yawast
463
575
  Yawast::Utilities.puts_info "\t\t\tPOODLE (TLS): No"
464
576
  when 2
465
577
  Yawast::Utilities.puts_vuln "\t\t\tPOODLE (TLS): Vulnerable"
578
+
579
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
580
+ 'tls_poodle',
581
+ {vulnerable: true}
466
582
  else
467
583
  Yawast::Utilities.puts_error "\t\t\tPOODLE (TLS): Unknown Response #{ep['details']['poodleTls']}"
468
584
  end
469
585
 
470
586
  if ep['details']['fallbackScsv']
471
587
  Yawast::Utilities.puts_info "\t\t\tDowngrade Prevention: Yes"
588
+
589
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
590
+ 'tls_missing_fallback_scsv',
591
+ {vulnerable: false}
472
592
  else
473
593
  Yawast::Utilities.puts_warn "\t\t\tDowngrade Prevention: No"
594
+
595
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
596
+ 'tls_missing_fallback_scsv',
597
+ {vulnerable: true}
474
598
  end
475
599
 
476
600
  if ep['details']['compressionMethods'] & 1 != 0
477
601
  Yawast::Utilities.puts_warn "\t\t\tCompression: DEFLATE"
602
+
603
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
604
+ 'tls_compression_enabled',
605
+ {vulnerable: true}
478
606
  else
479
607
  Yawast::Utilities.puts_info "\t\t\tCompression: No"
608
+
609
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
610
+ 'tls_compression_enabled',
611
+ {vulnerable: false}
480
612
  end
481
613
 
482
614
  if ep['details']['heartbeat']
483
615
  Yawast::Utilities.puts_warn "\t\t\tHeartbeat: Enabled"
616
+
617
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
618
+ 'tls_heartbeat_enabled',
619
+ {vulnerable: true}
484
620
  else
485
621
  Yawast::Utilities.puts_info "\t\t\tHeartbeat: Disabled"
622
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
623
+ 'tls_heartbeat_enabled',
624
+ {vulnerable: false}
486
625
  end
487
626
 
488
627
  if ep['details']['heartbleed']
489
628
  Yawast::Utilities.puts_vuln "\t\t\tHeartbleed: Vulnerable"
629
+
630
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
631
+ 'tls_heartblead',
632
+ {vulnerable: true}
490
633
  else
491
634
  Yawast::Utilities.puts_info "\t\t\tHeartbleed: No"
635
+
636
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
637
+ 'tls_heartblead',
638
+ {vulnerable: false}
492
639
  end
493
640
 
641
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
642
+ 'tls_ticketbleed',
643
+ {vulnerable: false}
494
644
  case ep['details']['ticketbleed']
495
645
  when -1
496
646
  Yawast::Utilities.puts_error "\t\t\tTicketbleed (CVE-2016-9244): Test Failed"
@@ -500,11 +650,17 @@ module Yawast
500
650
  Yawast::Utilities.puts_info "\t\t\tTicketbleed (CVE-2016-9244): No"
501
651
  when 2
502
652
  Yawast::Utilities.puts_vuln "\t\t\tTicketbleed (CVE-2016-9244): Vulnerable"
653
+
654
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
655
+ 'tls_ticketbleed',
656
+ {vulnerable: true}
503
657
  else
504
658
  Yawast::Utilities.puts_error "\t\t\tTicketbleed (CVE-2016-9244): Unknown Response #{ep['details']['ticketbleed']}"
505
659
  end
506
660
 
507
-
661
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
662
+ 'tls_openssl_ccs_cve20140224',
663
+ {vulnerable: false, exploitable: false}
508
664
  case ep['details']['openSslCcs']
509
665
  when -1
510
666
  Yawast::Utilities.puts_error "\t\t\tOpenSSL CCS (CVE-2014-0224): Test Failed"
@@ -514,12 +670,24 @@ module Yawast
514
670
  Yawast::Utilities.puts_info "\t\t\tOpenSSL CCS (CVE-2014-0224): No"
515
671
  when 2
516
672
  Yawast::Utilities.puts_vuln "\t\t\tOpenSSL CCS (CVE-2014-0224): Vulnerable - Not Exploitable"
673
+
674
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
675
+ 'tls_openssl_ccs_cve20140224',
676
+ {vulnerable: true, exploitable: false}
517
677
  when 3
518
678
  Yawast::Utilities.puts_vuln "\t\t\tOpenSSL CCS (CVE-2014-0224): Vulnerable"
679
+
680
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
681
+ 'tls_openssl_ccs_cve20140224',
682
+ {vulnerable: true, exploitable: true}
519
683
  else
520
684
  Yawast::Utilities.puts_error "\t\t\tOpenSSL CCS (CVE-2014-0224): Unknown Response #{ep['details']['openSslCcs']}"
521
685
  end
522
686
 
687
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
688
+ 'tls_openssl_lunckyminus20',
689
+ {vulnerable: false}
690
+
523
691
  case ep['details']['openSSLLuckyMinus20']
524
692
  when -1
525
693
  Yawast::Utilities.puts_error "\t\t\tOpenSSL Padding Oracle (CVE-2016-2107): Test Failed"
@@ -529,10 +697,17 @@ module Yawast
529
697
  Yawast::Utilities.puts_info "\t\t\tOpenSSL Padding Oracle (CVE-2016-2107): No"
530
698
  when 2
531
699
  Yawast::Utilities.puts_vuln "\t\t\tOpenSSL Padding Oracle (CVE-2016-2107): Vulnerable"
700
+
701
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
702
+ 'tls_openssl_lunckyminus20',
703
+ {vulnerable: true}
532
704
  else
533
705
  Yawast::Utilities.puts_error "\t\t\tOpenSSL Padding Oracle (CVE-2016-2107): Unknown Response #{ep['details']['openSSLLuckyMinus20']}"
534
706
  end
535
707
 
708
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
709
+ 'tls_robot',
710
+ {vulnerable: false, exploitable: false}
536
711
  case ep['details']['bleichenbacher']
537
712
  when -1
538
713
  Yawast::Utilities.puts_error "\t\t\tROBOT: Test Failed"
@@ -542,28 +717,66 @@ module Yawast
542
717
  Yawast::Utilities.puts_info "\t\t\tROBOT: No"
543
718
  when 2
544
719
  Yawast::Utilities.puts_warn "\t\t\tROBOT: Not Exploitable"
720
+
721
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
722
+ 'tls_robot',
723
+ {vulnerable: true, exploitable: false}
545
724
  when 3
546
725
  Yawast::Utilities.puts_vuln "\t\t\tROBOT: Exploitable"
726
+
727
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
728
+ 'tls_robot',
729
+ {vulnerable: true, exploitable: true}
547
730
  when nil
548
731
  # if it's null, we don't care
549
732
  else
550
733
  Yawast::Utilities.puts_error "\t\t\tROBOT: Unknown Response #{ep['details']['bleichenbacher']}"
551
734
  end
552
735
 
553
- if ep['details']['forwardSecrecy'] & (1<<2) != 0
736
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
737
+ 'tls_missing_forward_secrecy',
738
+ {vulnerable: false}
739
+
740
+ if ep['details']['forwardSecrecy'] & (1 << 2) != 0
554
741
  Yawast::Utilities.puts_info "\t\t\tForward Secrecy: Yes (all simulated clients)"
555
- elsif ep['details']['forwardSecrecy'] & (1<<1) != 0
742
+ elsif ep['details']['forwardSecrecy'] & (1 << 1) != 0
556
743
  Yawast::Utilities.puts_info "\t\t\tForward Secrecy: Yes (modern clients)"
557
744
  elsif ep['details']['forwardSecrecy'] & 1 != 0
558
745
  Yawast::Utilities.puts_warn "\t\t\tForward Secrecy: Yes (limited support)"
746
+
747
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
748
+ 'tls_missing_forward_secrecy',
749
+ {vulnerable: true}
559
750
  else
560
751
  Yawast::Utilities.puts_vuln "\t\t\tForward Secrecy: No"
752
+
753
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
754
+ 'tls_missing_forward_secrecy',
755
+ {vulnerable: true}
756
+ end
757
+
758
+ if ep['details']['supportsAead']
759
+ Yawast::Utilities.puts_info "\t\t\tAEAD Cipher Suites Supported: Yes"
760
+
761
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
762
+ 'tls_aead_support_missing',
763
+ {vulnerable: false}
764
+ else
765
+ Yawast::Utilities.puts_warn "\t\t\tAEAD Cipher Suites Supported: No"
766
+
767
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
768
+ 'tls_aead_support_missing',
769
+ {vulnerable: true}
561
770
  end
562
771
 
563
772
  Yawast::Utilities.puts_info "\t\t\tALPN: #{ep['details']['alpnProtocols']}"
564
773
 
565
774
  Yawast::Utilities.puts_info "\t\t\tNPN: #{ep['details']['npnProtocols']}"
566
775
 
776
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
777
+ 'tls_session_resumption',
778
+ {vulnerable: false}
779
+
567
780
  case ep['details']['sessionResumption']
568
781
  when 0
569
782
  Yawast::Utilities.puts_info "\t\t\tSession Resumption: Not Enabled / Empty Tickets"
@@ -571,52 +784,64 @@ module Yawast
571
784
  Yawast::Utilities.puts_info "\t\t\tSession Resumption: Enabled / No Resumption"
572
785
  when 2
573
786
  Yawast::Utilities.puts_warn "\t\t\tSession Resumption: Enabled"
787
+
788
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
789
+ 'tls_session_resumption',
790
+ {vulnerable: true}
574
791
  else
575
792
  Yawast::Utilities.puts_error "\t\t\tSession Resumption: Unknown Response #{ep['details']['sessionResumption']}"
576
793
  end
577
794
 
578
795
  if ep['details']['ocspStapling']
579
796
  Yawast::Utilities.puts_info "\t\t\tOCSP Stapling: Yes"
797
+
798
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
799
+ 'tls_ocsp_stapling_missing',
800
+ {vulnerable: false}
580
801
  else
581
802
  Yawast::Utilities.puts_warn "\t\t\tOCSP Stapling: No"
803
+
804
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
805
+ 'tls_ocsp_stapling_missing',
806
+ {vulnerable: true}
582
807
  end
583
808
 
584
- if ep['details']['miscIntolerance'] > 0
809
+ if ep['details']['miscIntolerance'].positive?
585
810
  if ep['details']['miscIntolerance'] & 1 != 0
586
811
  Yawast::Utilities.puts_warn "\t\t\tTLS Extension Intolerance: Yes"
587
812
  end
588
813
 
589
- if ep['details']['miscIntolerance'] & (1<<1) != 0
814
+ if ep['details']['miscIntolerance'] & (1 << 1) != 0
590
815
  Yawast::Utilities.puts_warn "\t\t\tLong Handshake Intolerance: Yes"
591
816
  end
592
817
 
593
- if ep['details']['miscIntolerance'] & (1<<2) != 0
818
+ if ep['details']['miscIntolerance'] & (1 << 2) != 0
594
819
  Yawast::Utilities.puts_warn "\t\t\tLong Handshake Intolerance: Workaround Success"
595
820
  end
596
821
  end
597
822
 
598
- if ep['details']['protocolIntolerance'] > 0
823
+ if ep['details']['protocolIntolerance'].positive?
599
824
  if ep['details']['protocolIntolerance'] & 1 != 0
600
825
  Yawast::Utilities.puts_warn "\t\t\tProtocol Intolerance: TLS 1.0"
601
826
  end
602
827
 
603
- if ep['details']['protocolIntolerance'] & (1<<1) != 0
828
+ if ep['details']['protocolIntolerance'] & (1 << 1) != 0
604
829
  Yawast::Utilities.puts_warn "\t\t\tProtocol Intolerance: TLS 1.1"
605
830
  end
606
831
 
607
- if ep['details']['protocolIntolerance'] & (1<<2) != 0
832
+ if ep['details']['protocolIntolerance'] & (1 << 2) != 0
608
833
  Yawast::Utilities.puts_warn "\t\t\tProtocol Intolerance: TLS 1.2"
609
834
  end
610
835
 
611
- if ep['details']['protocolIntolerance'] & (1<<3) != 0
836
+ if ep['details']['protocolIntolerance'] & (1 << 3) != 0
612
837
  Yawast::Utilities.puts_warn "\t\t\tProtocol Intolerance: TLS 1.3"
613
838
  end
614
839
 
615
- if ep['details']['protocolIntolerance'] & (1<<4) != 0
840
+ if ep['details']['protocolIntolerance'] & (1 << 4) != 0
616
841
  Yawast::Utilities.puts_warn "\t\t\tProtocol Intolerance: TLS 1.152"
617
842
  end
618
843
 
619
- if ep['details']['protocolIntolerance'] & (1<<5) != 0
844
+ if ep['details']['protocolIntolerance'] & (1 << 5) != 0
620
845
  Yawast::Utilities.puts_warn "\t\t\tProtocol Intolerance: TLS 2.152"
621
846
  end
622
847
  else
@@ -625,39 +850,83 @@ module Yawast
625
850
 
626
851
  if ep['details']['freak']
627
852
  Yawast::Utilities.puts_vuln "\t\t\tFREAK: Vulnerable (512-bit key exchange supported)"
853
+
854
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
855
+ 'tls_freak',
856
+ {vulnerable: true}
628
857
  else
629
858
  Yawast::Utilities.puts_info "\t\t\tFREAK: No"
859
+
860
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
861
+ 'tls_freak',
862
+ {vulnerable: false}
630
863
  end
631
864
 
632
865
  if ep['details']['logjam']
633
866
  Yawast::Utilities.puts_vuln "\t\t\tLogjam: Vulnerable (DH key exchange with keys smaller than 1024 bits)"
867
+
868
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
869
+ 'tls_logjam',
870
+ {vulnerable: true}
634
871
  else
635
872
  Yawast::Utilities.puts_info "\t\t\tLogjam: No"
873
+
874
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
875
+ 'tls_logjam',
876
+ {vulnerable: false}
636
877
  end
637
878
 
879
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
880
+ 'tls_dh_known_primes',
881
+ {vulnerable: false, weak: false}
882
+
638
883
  case ep['details']['dhUsesKnownPrimes']
639
884
  when 0
640
885
  Yawast::Utilities.puts_info "\t\t\tUses common DH primes: No"
641
886
  when 1
642
887
  Yawast::Utilities.puts_warn "\t\t\tUses common DH primes: Yes (not weak)"
888
+
889
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
890
+ 'tls_dh_known_primes',
891
+ {vulnerable: true, weak: false}
643
892
  when 2
644
893
  Yawast::Utilities.puts_vuln "\t\t\tUses common DH primes: Yes (weak)"
894
+
895
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
896
+ 'tls_dh_known_primes',
897
+ {vulnerable: true, weak: true}
645
898
  else
646
- unless ep['details']['dhUsesKnownPrimes'] == nil
899
+ unless ep['details']['dhUsesKnownPrimes'].nil?
647
900
  Yawast::Utilities.puts_error "\t\t\tUses common DH primes: Unknown Response #{ep['details']['dhUsesKnownPrimes']}"
648
901
  end
649
902
  end
650
903
 
651
904
  if ep['details']['dhYsReuse']
652
905
  Yawast::Utilities.puts_vuln "\t\t\tDH public server param (Ys) reuse: Yes"
906
+
907
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
908
+ 'tls_dh_public_server_param_reuse',
909
+ {vulnerable: true}
653
910
  else
654
911
  Yawast::Utilities.puts_info "\t\t\tDH public server param (Ys) reuse: No"
912
+
913
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
914
+ 'tls_dh_public_server_param_reuse',
915
+ {vulnerable: false}
655
916
  end
656
917
 
657
918
  if ep['details']['ecdhParameterReuse']
658
919
  Yawast::Utilities.puts_vuln "\t\t\tECDH Public Server Param Reuse: Yes"
920
+
921
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
922
+ 'tls_ecdh_public_server_param_reuse',
923
+ {vulnerable: true}
659
924
  else
660
925
  Yawast::Utilities.puts_info "\t\t\tECDH Public Server Param Reuse: No"
926
+
927
+ Yawast::Shared::Output.log_hash 'vulnerabilities',
928
+ 'tls_ecdh_public_server_param_reuse',
929
+ {vulnerable: false}
661
930
  end
662
931
 
663
932
  puts
@@ -667,32 +936,26 @@ module Yawast
667
936
  secure = true
668
937
 
669
938
  # check for weak DH
670
- if suite['kxStrength'] != nil && suite['kxStrength'] < 2048
671
- secure = false
672
- end
939
+ secure = false if !suite['kxStrength'].nil? && suite['kxStrength'] < 2048
673
940
  # check for RC4
674
- if suite['name'].include? 'RC4'
675
- secure = false
676
- end
941
+ secure = false if suite['name'].include? 'RC4'
677
942
  # check for weak suites
678
- if suite['cipherStrength'] < 112
679
- secure = false
680
- end
943
+ secure = false if suite['cipherStrength'] < 112
681
944
 
682
945
  secure
683
946
  end
684
947
 
685
948
  def self.get_key_exchange(suite)
686
949
  ke = nil
687
- if suite['kxType'] != nil
688
- if suite['namedGroupBits'] != nil
689
- ke = "#{suite['kxType']}-#{suite['namedGroupBits']} / #{suite['namedGroupName']} (#{suite['kxStrength']} equivalent)"
690
- else
691
- ke = "#{suite['kxType']}-#{suite['kxStrength']}"
692
- end
950
+ unless suite['kxType'].nil?
951
+ ke = if !suite['namedGroupBits'].nil?
952
+ "#{suite['kxType']}-#{suite['namedGroupBits']} / #{suite['namedGroupName']} (#{suite['kxStrength']} equivalent)"
953
+ else
954
+ "#{suite['kxType']}-#{suite['kxStrength']}"
955
+ end
693
956
  end
694
957
 
695
- return ke
958
+ ke
696
959
  end
697
960
  end
698
961
  end