parent
0559ed0597
commit
340c4a445d
@ -1,38 +1,57 @@ |
||||
PWD = $(shell pwd)
|
||||
export CPATH = $(PWD)/openssl/include
|
||||
export LIBRARY_PATH = $(PWD)/openssl
|
||||
OPENSSL_VERSION = OpenSSL_1_0_1j
|
||||
RUBY_VERSION = 2.1.5
|
||||
RUBY_OPENSSL_EXT_DIR = ruby-$(RUBY_VERSION)/ext/openssl
|
||||
OPENSSL_VERSION = 1.0.1m
|
||||
OPENSSL_DIR = openssl-$(OPENSSL_VERSION)
|
||||
RUBY_MAJOR_VERSION = 2.2
|
||||
RUBY_VERSION = $(RUBY_MAJOR_VERSION).2
|
||||
RUBY_DIR = ruby-$(RUBY_VERSION)
|
||||
RUBY_OPENSSL_EXT_DIR = $(RUBY_DIR)/ext/openssl
|
||||
export LIBRARY_PATH = $(PWD)/lib
|
||||
export C_INCLUDE_PATH = $(PWD)/$(OPENSSL_DIR)/include
|
||||
|
||||
all: lib/libssl.so.1.0.0 lib/libcrypto.so.1.0.0 lib/openssl.so |
||||
.SECONDARY: |
||||
|
||||
all: libs ext |
||||
|
||||
clean: |
||||
rm -rf ruby-$(RUBY_VERSION) openssl
|
||||
rm -rf $(RUBY_DIR) $(OPENSSL_DIR)
|
||||
|
||||
mr-proper: clean |
||||
rm -rf lib/libcrypto.so* lib/libssl.so* lib/openssl.so
|
||||
|
||||
$(OPENSSL_DIR)/: |
||||
wget https://www.openssl.org/source/$(OPENSSL_DIR).tar.gz
|
||||
tar xf $(OPENSSL_DIR).tar.gz
|
||||
rm -rf $(OPENSSL_DIR).tar.gz
|
||||
|
||||
openssl: |
||||
git clone https://github.com/openssl/openssl -b $(OPENSSL_VERSION)
|
||||
$(OPENSSL_DIR)/Makefile: $(OPENSSL_DIR)/ |
||||
cd $(OPENSSL_DIR); ./config shared
|
||||
|
||||
openssl/Makefile: openssl |
||||
cd openssl; ./config shared
|
||||
$(OPENSSL_DIR)/libssl.so.1.0.0 $(OPENSSL_DIR)/libcrypto.so.1.0.0: $(OPENSSL_DIR)/Makefile |
||||
$(MAKE) -C $(OPENSSL_DIR) depend build_libs
|
||||
|
||||
openssl/libssl.so: openssl/Makefile |
||||
cd openssl; $(MAKE) depend all
|
||||
lib/%.so.1.0.0: $(OPENSSL_DIR)/%.so.1.0.0 |
||||
cp $< $@
|
||||
|
||||
lib/%.so: lib/%.so.1.0.0 |
||||
ln -s $(notdir $<) $@
|
||||
|
||||
lib/%.so.1.0.0: openssl/%.so |
||||
cp $^ $@
|
||||
libs: lib/libssl.so lib/libcrypto.so |
||||
|
||||
ruby-$(RUBY_VERSION): |
||||
wget http://cache.ruby-lang.org/pub/ruby/2.1/ruby-$(RUBY_VERSION).tar.gz
|
||||
tar xf ruby-$(RUBY_VERSION).tar.gz
|
||||
rm -f ruby-$(RUBY_VERSION).tar.gz
|
||||
$(RUBY_DIR): |
||||
wget http://cache.ruby-lang.org/pub/ruby/$(RUBY_MAJOR_VERSION)/$(RUBY_DIR).tar.gz
|
||||
tar xf $(RUBY_DIR).tar.gz
|
||||
rm -f $(RUBY_DIR).tar.gz
|
||||
|
||||
$(RUBY_OPENSSL_EXT_DIR)/Makefile: ruby-$(RUBY_VERSION) |
||||
$(RUBY_OPENSSL_EXT_DIR)/Makefile: libs $(RUBY_DIR) |
||||
cd $(RUBY_OPENSSL_EXT_DIR); ruby extconf.rb
|
||||
patch $@ patch
|
||||
|
||||
$(RUBY_OPENSSL_EXT_DIR)/openssl.so: $(RUBY_OPENSSL_EXT_DIR)/Makefile |
||||
cd $(RUBY_OPENSSL_EXT_DIR); $(MAKE); $(MAKE) install
|
||||
$(RUBY_OPENSSL_EXT_DIR)/openssl.so: libs $(RUBY_OPENSSL_EXT_DIR)/Makefile |
||||
$(MAKE) -C $(RUBY_OPENSSL_EXT_DIR)
|
||||
|
||||
lib/openssl.so: $(RUBY_OPENSSL_EXT_DIR)/openssl.so |
||||
cp $< $@
|
||||
|
||||
ext: lib/openssl.so |
@ -0,0 +1,17 @@ |
||||
#!/usr/bin/env ruby |
||||
$:.unshift 'lib' |
||||
require 'logging' |
||||
require 'cryptcheck' |
||||
|
||||
name = ARGV[0] |
||||
unless name |
||||
::CryptCheck::Tls::Smtp.analyze_from_file 'output/smtp.yml', 'output/smtp.html' |
||||
else |
||||
::Logging.logger.root.appenders = ::Logging.appenders.stdout |
||||
::Logging.logger.root.level = :warn |
||||
|
||||
server = ::CryptCheck::Tls::Smtp::Server.new(ARGV[0], ARGV[1] || 25) |
||||
p grade = ::CryptCheck::Tls::Smtp::Grade.new(server) |
||||
end |
||||
|
||||
|
@ -0,0 +1,71 @@ |
||||
require 'erb' |
||||
require 'logging' |
||||
require 'parallel' |
||||
|
||||
module CryptCheck |
||||
module Tls |
||||
MAX_ANALYSIS_DURATION = 600 |
||||
PARALLEL_ANALYSIS = 10 |
||||
@@log = ::Logging.logger[Tls] |
||||
|
||||
def self.grade(hostname, port, server_class:, grade_class:) |
||||
timeout MAX_ANALYSIS_DURATION do |
||||
grade_class.new server_class.new hostname, port |
||||
end |
||||
rescue ::Exception => e |
||||
@@log.error { "Error during #{hostname}:#{port} analysis : #{e}" } |
||||
TlsNotSupportedGrade.new TlsNotSupportedServer.new hostname, port |
||||
end |
||||
|
||||
def self.analyze(hosts, template, output, groups = nil, port:, server_class:, grade_class:) |
||||
results = {} |
||||
semaphore = ::Mutex.new |
||||
::Parallel.each hosts, progress: 'Analysing', in_threads: PARALLEL_ANALYSIS, finish: lambda { |item, _, _| puts item[1] } do |description, host| |
||||
result = grade host.strip, port, server_class: server_class, grade_class: grade_class |
||||
semaphore.synchronize do |
||||
if results.include? description |
||||
results[description] << result |
||||
else |
||||
results[description] = [result] |
||||
end |
||||
end |
||||
end |
||||
|
||||
results = ::Hash[groups.collect { |g| [g, results[g]] }] if groups |
||||
|
||||
results.each do |d, _| |
||||
results[d].sort! do |a, b| |
||||
cmp = score(a) <=> score(b) |
||||
if cmp == 0 |
||||
cmp = b.score <=> a.score |
||||
if cmp == 0 |
||||
cmp = a.server.hostname <=> b.server.hostname |
||||
end |
||||
end |
||||
cmp |
||||
end |
||||
end |
||||
|
||||
::File.write output, ::ERB.new(::File.read(template)).result(binding) |
||||
end |
||||
|
||||
def self.analyze_from_file(file, template, output, port:, server_class:, grade_class:) |
||||
config = ::YAML.load_file file |
||||
hosts = [] |
||||
groups = [] |
||||
config.each do |c| |
||||
d, hs = c['description'], c['hostnames'] |
||||
groups << d |
||||
hs.each { |host| hosts << [d, host] } |
||||
end |
||||
self.analyze hosts, template, output, groups, port: port, server_class: server_class, grade_class: grade_class |
||||
end |
||||
|
||||
private |
||||
SCORES = %w(A+ A A- B C D E F T M X) |
||||
|
||||
def self.score(a) |
||||
SCORES.index a.grade |
||||
end |
||||
end |
||||
end |
@ -0,0 +1,9 @@ |
||||
module CryptCheck |
||||
module Tls |
||||
module Smtp |
||||
def self.analyze_from_file(file, output) |
||||
Tls.analyze_from_file file, 'output/smtp.erb', output, port: 25, server_class: Server, grade_class: Grade |
||||
end |
||||
end |
||||
end |
||||
end |
@ -0,0 +1,8 @@ |
||||
module CryptCheck |
||||
module Tls |
||||
module Smtp |
||||
class Grade < Tls::Grade |
||||
end |
||||
end |
||||
end |
||||
end |
@ -0,0 +1,69 @@ |
||||
- description: Autorités de certification |
||||
hostnames: |
||||
- www.cacert.org |
||||
- acedicom.edicomgroup.com |
||||
- grca.nat.gov.tw |
||||
- pki.atos.net |
||||
- www.bundesdruckerei.de |
||||
- www.cybertrust.ne.jp |
||||
- www.logius.nl |
||||
- www.procert.net.ve |
||||
- www.s-trust.de |
||||
- webappsecurity.trendmicro.com |
||||
- www1.cnnic.cn |
||||
- www.actalis.it |
||||
- www.aoc.cat |
||||
- www.a-trust.at |
||||
- www.buypass.no |
||||
- www.camerfirma.com |
||||
- www.certicamara.com |
||||
- www.certigna.fr |
||||
- www.certinomis.com |
||||
- www.certsign.ro |
||||
- www.certum.pl |
||||
- www.cfca.com.cn |
||||
- www.cht.com.tw |
||||
- www.comodo.com |
||||
- www.comsign.co.il |
||||
- www.digicert.com |
||||
- www.disig.eu |
||||
- www.emc.com |
||||
- www.entrust.net |
||||
- www.e-szigno.hu |
||||
- www.etugra.com.tr |
||||
- www.firmaprofesional.com |
||||
- www.geotrust.com |
||||
- www.globalsign.com |
||||
- www.godaddy.com |
||||
- www.gpki.go.jp |
||||
- www.harica.gr |
||||
- www.hongkongpost.gov.hk |
||||
- www.identrust.com |
||||
- www.izenpe.com |
||||
- www.kamusm.gov.tr |
||||
- www.netlock.hu |
||||
- www.networksolutions.com |
||||
- www.opentrust.com |
||||
- www.pki.gva.es |
||||
- www.quovadisglobal.com |
||||
- www.secomtrust.net |
||||
- www.sgtrustservices.com |
||||
- www.sk.ee |
||||
- www.ssi.gouv.fr |
||||
- www.startssl.com |
||||
- www.swissdigicert.ch |
||||
- www.swisssign.com |
||||
- www.symantec.com |
||||
- www.teliasonera.com |
||||
- www.thawte.com |
||||
- www.trustcenter.de |
||||
- www.trustis.com |
||||
- www.trustwave.com |
||||
- www.t-systems.com |
||||
- www.turktrust.com.tr |
||||
- www.twca.com.tw |
||||
- www.verizon.com |
||||
- www.visa.com |
||||
- www.wellsfargo.com |
||||
- www.wisekey.com |
||||
- www.wosign.com |
@ -0,0 +1,35 @@ |
||||
- description: Journaux & Presse en ligne |
||||
hostnames: |
||||
- charliehebdo.fr |
||||
- tempsreel.nouvelobs.com |
||||
- www.20minutes.fr |
||||
- www.challenges.fr |
||||
- www.courrierinternational.com |
||||
- www.directmatin.fr |
||||
- www.francesoir.fr |
||||
- www.humanite.presse.fr |
||||
- www.la-croix.com |
||||
- www.latribune.fr |
||||
- www.lecanardenchaine.fr |
||||
- www.lefigaro.fr |
||||
- www.lejdd.fr |
||||
- www.lemonde.fr |
||||
- www.leparisien.fr |
||||
- www.lepoint.fr |
||||
- www.lequipe.fr |
||||
- www.lesechos.fr |
||||
- www.lexpress.fr |
||||
- www.liberation.fr |
||||
- www.lopinion.fr |
||||
- www.marianne.net |
||||
- www.mediapart.fr |
||||
- www.metronews.fr |
||||
- www.minute-hebdo.fr |
||||
- www.monde-diplomatique.fr |
||||
- www.monde-libertaire.fr |
||||
- www.parismatch.com |
||||
- www.telerama.fr |
||||
- www.vsd.fr |
||||
- www.slate.fr |
||||
- reader.fr |
||||
- www.arretsurimages.net |
@ -0,0 +1,25 @@ |
||||
- description: SecureDrop instances |
||||
hostnames: |
||||
- securedrop.propublica.org |
||||
- ssl.washingtonpost.com |
||||
- nrkbeta.no |
||||
- exposefacts.org |
||||
- firstlook.org |
||||
- www.safesource.org.nz |
||||
- safesource.forbes.com |
||||
- pressfreedomfoundation.org |
||||
- projects.newyorker.com |
||||
- securedrop.theguardian.com |
||||
- securedrop.pogo.org |
||||
- bayleaks.com |
||||
- securedrop.radio24syv.dk |
||||
- tcfmailvault.info |
||||
- www.balkanleaks.eu |
||||
- description: GlobalLeaks instances |
||||
hostnames: |
||||
- secure.publeaks.nl |
||||
- secure.wildleaks.org |
||||
- www.extremeleaks.org |
||||
- description: Misc |
||||
hostnames: |
||||
- secure.frenchleaks.fr |
@ -0,0 +1,192 @@ |
||||
<!DOCTYPE html> |
||||
<html lang="fr"> |
||||
<head> |
||||
<meta charset="utf-8"> |
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge"> |
||||
<meta name="viewport" content="width=device-width, initial-scale=1"> |
||||
<title>SSL/TLS — SMTP</title> |
||||
<link rel="stylesheet" href="bootstrap.min.css"> |
||||
<style> |
||||
body { |
||||
margin-top: 10px; |
||||
} |
||||
|
||||
td { |
||||
text-align: center; |
||||
} |
||||
|
||||
.critical { |
||||
background-color: #000; |
||||
color: #fff; |
||||
} |
||||
|
||||
tr:hover > td.critical, td:hover.critical { |
||||
background-color: #333 !important; |
||||
} |
||||
</style> |
||||
</head> |
||||
<body> |
||||
<div class="container-fluid"> |
||||
<div class="row"> |
||||
<div class="col-md-12"> |
||||
<table class="table table-bordered table-hover table-condensed"> |
||||
<tbody> |
||||
<% |
||||
first = true |
||||
results.each do |r| |
||||
unless first |
||||
%> |
||||
<tr> |
||||
<th colspan="15"> </th> |
||||
</tr> |
||||
<% |
||||
end |
||||
first = false |
||||
%> |
||||
<tr> |
||||
<th colspan="14" id="<%= r[0] %>"><%= r[0] %></th> |
||||
</tr> |
||||
<tr> |
||||
<th rowspan="2">Site</th> |
||||
<td rowspan="2">Grade</td> |
||||
<td colspan="2">Certificate</td> |
||||
<td colspan="4">Protocols</td> |
||||
<td colspan="5">Ciphers</td> |
||||
<td>Best practices</td> |
||||
</tr> |
||||
<tr> |
||||
<td>Key size (bits)</td> |
||||
<td class="warning">SHA1 sig</td> |
||||
|
||||
<td class="critical">SSL v2</td> |
||||
<td class="critical">SSL v3</td> |
||||
<td class="success">TLS 1.2</td> |
||||
<td class="info">TLS</td> |
||||
|
||||
<td>Strength (bits)</td> |
||||
<td class="critical">MD5</td> |
||||
<td class="warning">SHA1</td> |
||||
<td class="critical">DES/RC4</td> |
||||
<td class="danger">3DES</td> |
||||
|
||||
<td class="info">PFS</td> |
||||
</tr> |
||||
<% r[1].each do |n| |
||||
s = n.server |
||||
%> |
||||
<tr> |
||||
<% if s.is_a? Tls::TlsNotSupportedServer %> |
||||
<th id="<%= s.hostname %>"> |
||||
<a href="#<%= s.hostname %>"><%= s.hostname %></a> |
||||
</th> |
||||
<td class="critical" colspan="16"> |
||||
No SSL/TLS |
||||
</td> |
||||
<% |
||||
else |
||||
rank_color = case n.grade |
||||
when 'A+' then :info |
||||
when 'A', 'A-' then :success |
||||
when 'B', 'C' then :warning |
||||
when 'T', 'M' then :critical |
||||
else :danger |
||||
end |
||||
%> |
||||
<th id="<%= s.domain %>"><%= s.domain %></th> |
||||
<td class="<%= rank_color %>"> |
||||
<%= n.grade %> |
||||
</td> |
||||
|
||||
<td class="<%= s.key_size < 2048 ? :danger : s.key_size < 4096 ? :warning : :success %>"> |
||||
<% type, size = s.key %> |
||||
<%= "#{size} (#{type.to_s.upcase})" %> |
||||
<span class="sr-only">(<%= s.key_size < 2048 ? '☹' : '☺' %>)</span> |
||||
</td> |
||||
<td class="<%= s.sha1_sig? ? :warning : :success %>"> |
||||
<%= s.sha1_sig? ? '✓' : '✗' %> |
||||
<span class="sr-only">(<%= s.sha1_sig? ? '☹' : '☺' %>)</span> |
||||
</td> |
||||
|
||||
<td class="<%= s.sslv2? ? :critical : :success %>"> |
||||
<%= s.sslv2? ? '✓' : '✗' %> |
||||
<span class="sr-only">(<%= s.sslv2? ? '☹' : '☺' %>)</span> |
||||
</td> |
||||
<td class="<%= s.sslv3? ? :critical : :success %>"> |
||||
<%= s.sslv3? ? '✓' : '✗' %> |
||||
<span class="sr-only">(<%= s.sslv3? ? '☹' : '☺' %>)</span> |
||||
</td> |
||||
<td class="<%= s.tlsv1_2? ? :success : :danger %>"> |
||||
<%= s.tlsv1_2? ? '✓' : '✗' %> |
||||
<span class="sr-only">(<%= s.tlsv1_2? ? '☺' : '☹' %>)</span> |
||||
</td> |
||||
<td class="<%= s.tls? ? (s.tls_only? ? :info : :success) : :danger %>"> |
||||
<%= s.tls? ? '✓' : '✗' %> |
||||
<span class="sr-only">(<%= s.tls? ? '☺' : '☹' %>)</span> |
||||
</td> |
||||
|
||||
<% cipher_size = s.cipher_size[:worst] %> |
||||
<td class="<%= cipher_size < 112 ? :danger : cipher_size < 128 ? :warning : :success %>"> |
||||
<%= cipher_size %> |
||||
<span class="sr-only">(<%= cipher_size < 128 ? '☹' : '☺' %>)</span> |
||||
</td> |
||||
<td class="<%= s.md5? ? :critical : :success %>"> |
||||
<%= s.md5? ? '✓' : '✗' %> |
||||
<span class="sr-only">(<%= s.md5? ? '☹' : '☺' %>)</span> |
||||
</td> |
||||
<td class="<%= s.sha1? ? :warning : :success %>"> |
||||
<%= s.sha1? ? '✓' : '✗' %> |
||||
<span class="sr-only">(<%= s.sha1? ? '☹' : '☺' %>)</span> |
||||
</td> |
||||
<td class="<%= (s.rc4? or s.des?) ? :critical : :success %>"> |
||||
<%= (s.rc4? or s.des?) ? '✓' : '✗' %> |
||||
<span class="sr-only">(<%= (s.rc4? or s.des?) ? '☹' : '☺' %>)</span> |
||||
</td> |
||||
<td class="<%= s.des3? ? :danger : :success %>"> |
||||
<%= s.des3? ? '✓' : '✗' %> |
||||
<span class="sr-only">(<%= s.des3? ? '☹' : '☺' %>)</span> |
||||
</td> |
||||
|
||||
<td class="<%= s.pfs? ? (s.pfs_only? ? :info : :success) : :danger %>"> |
||||
<%= s.pfs? ? '✓' : '✗' %> |
||||
<span class="sr-only">(<%= s.pfs? ? '☺' : '☹' %>)</span> |
||||
</td> |
||||
<% end %> |
||||
</tr> |
||||
<% end %> |
||||
<tr> |
||||
<th rowspan="2">Site</th> |
||||
<td rowspan="2">Grade</td> |
||||
|
||||
<td>Key size (bits)</td> |
||||
<td class="warning">SHA1 sig</td> |
||||
|
||||
<td class="critical">SSL v2</td> |
||||
<td class="critical">SSL v3</td> |
||||
<td class="success">TLS 1.2</td> |
||||
<td class="info">TLS</td> |
||||
|
||||
<td>Strength (bits)</td> |
||||
<td class="critical">MD5</td> |
||||
<td class="warning">SHA1</td> |
||||
<td class="critical">DES/RC4</td> |
||||
<td class="danger">3DES</td> |
||||
|
||||
<td class="info">PFS</td> |
||||
</tr> |
||||
<tr> |
||||
<td colspan="2">Certificate</td> |
||||
<td colspan="4">Protocols</td> |
||||
<td colspan="5">Ciphers</td> |
||||
<td>Best practices</td> |
||||
</tr> |
||||
<% end %> |
||||
</tbody> |
||||
</table> |
||||
<div class="pull-right"> |
||||
Generated on <%= Time.now.strftime '%FT%T%:z' %> |
||||
</div> |
||||
</div> |
||||
</div> |
||||
</div> |
||||
</body> |
||||
</html> |
Loading…
Reference in new issue