Commit 20576b62 authored by fedor.brunner's avatar fedor.brunner

Support for sha256 fingerprint.

Fixes #7628
parent ae10198a
......@@ -354,6 +354,7 @@ class Config:
'warn_when_insecure_ssl_connection': [ opt_bool, True, _('Show a warning dialog before using standard SSL library.') ],
'warn_when_insecure_password': [ opt_bool, True, _('Show a warning dialog before sending PLAIN password over a plain connection.') ],
'ssl_fingerprint_sha1': [ opt_str, '', '', True ],
'ssl_fingerprint_sha256': [ opt_str, '', '', True ],
'ignore_ssl_errors': [ opt_str, '', _('Space separated list of ssl errors to ignore.') ],
'use_srv': [ opt_bool, True, '', True ],
'use_custom_host': [ opt_bool, False, '', True ],
......
......@@ -1403,37 +1403,56 @@ class Connection(CommonConnection, ConnectionHandlers):
cert = con.Connection.ssl_certificate
if errnum > 0 and str(errnum) not in gajim.config.get_per('accounts',
self.name, 'ignore_ssl_errors').split():
text = _('The authenticity of the %s certificate could be invlid') \
text = _('The authenticity of the %s certificate could be invalid') \
% hostname
if errnum in ssl_error:
text += _('\nSSL Error: <b>%s</b>') % ssl_error[errnum]
else:
text += _('\nUnknown SSL error: %d') % errnum
fingerprint = cert.digest('sha1')
fingerprint_sha1 = cert.digest('sha1')
fingerprint_sha256 = cert.digest('sha256')
pem = OpenSSL.crypto.dump_certificate(OpenSSL.crypto.FILETYPE_PEM,
cert)
gajim.nec.push_incoming_event(SSLErrorEvent(None, conn=self,
error_text=text, error_num=errnum, cert=pem,
fingerprint=fingerprint, certificate=cert))
fingerprint_sha1=fingerprint_sha1,
fingerprint_sha256=fingerprint_sha256, certificate=cert))
return True
if cert:
fingerprint = cert.digest('sha1')
saved_fingerprint = gajim.config.get_per('accounts', self.name,
fingerprint_sha1 = cert.digest('sha1')
fingerprint_sha256 = cert.digest('sha256')
saved_fingerprint_sha1 = gajim.config.get_per('accounts', self.name,
'ssl_fingerprint_sha1')
if saved_fingerprint:
if saved_fingerprint_sha1:
# Check sha1 fingerprint
if fingerprint != saved_fingerprint:
if fingerprint_sha1 != saved_fingerprint_sha1:
gajim.nec.push_incoming_event(FingerprintErrorEvent(None,
conn=self, certificate=con.Connection.ssl_certificate,
new_fingerprint=fingerprint))
new_fingerprint_sha1=fingerprint_sha1,
new_fingerprint_sha256=fingerprint_sha256))
return True
else:
gajim.config.set_per('accounts', self.name,
'ssl_fingerprint_sha1', fingerprint)
'ssl_fingerprint_sha1', fingerprint_sha1)
saved_fingerprint_sha256 = gajim.config.get_per('accounts', self.name,
'ssl_fingerprint_sha256')
if saved_fingerprint_sha256:
# Check sha256 fingerprint
if fingerprint_sha256 != saved_fingerprint_sha256:
gajim.nec.push_incoming_event(FingerprintErrorEvent(None,
conn=self, certificate=con.Connection.ssl_certificate,
new_fingerprint_sha1=fingerprint_sha1,
new_fingerprint_sha256=fingerprint_sha256))
return True
else:
gajim.config.set_per('accounts', self.name,
'ssl_fingerprint_sha256', fingerprint_sha256)
if not check_X509.check_certificate(con.Connection.ssl_certificate,
hostname) and '100' not in gajim.config.get_per('accounts',
self.name, 'ignore_ssl_errors').split():
fingerprint = cert.digest('sha1')
fingerprint_sha1 = cert.digest('sha1')
pem = OpenSSL.crypto.dump_certificate(
OpenSSL.crypto.FILETYPE_PEM, cert)
txt = _('The authenticity of the %s certificate could be '
......@@ -1441,7 +1460,8 @@ class Connection(CommonConnection, ConnectionHandlers):
hostname
gajim.nec.push_incoming_event(SSLErrorEvent(None, conn=self,
error_text=txt, error_num=100, cert=pem,
fingerprint=fingerprint, certificate=cert))
fingerprint_sha1=fingerprint_sha1,
fingerprint_sha256=fingerprint_sha256, certificate=cert))
return True
self._register_handlers(con, con_type)
......
......@@ -1640,12 +1640,14 @@ class NewAccountConnectedEvent(nec.NetworkIncomingEvent):
self.ssl_msg = ssl_error.get(er, _('Unknown SSL error: %d') % \
self.errnum)
self.ssl_cert = ''
self.ssl_fingerprint = ''
self.ssl_fingerprint_sha1 = ''
self.ssl_fingerprint_sha256 = ''
if self.conn.connection.Connection.ssl_certificate:
cert = self.conn.connection.Connection.ssl_certificate
self.ssl_cert = OpenSSL.crypto.dump_certificate(
OpenSSL.crypto.FILETYPE_PEM, cert)
self.ssl_fingerprint = cert.digest('sha1')
self.ssl_fingerprint_sha1 = cert.digest('sha1')
self.ssl_fingerprint_sha256 = cert.digest('sha1')
return True
class NewAccountNotConnectedEvent(nec.NetworkIncomingEvent):
......
......@@ -3789,7 +3789,9 @@ class AccountCreationWizardWindow:
f.write(self.ssl_cert + '\n\n')
f.close()
gajim.connections[self.account].new_account_info[
'ssl_fingerprint_sha1'] = self.ssl_fingerprint
'ssl_fingerprint_sha1'] = self.ssl_fingerprint_sha1
gajim.connections[self.account].new_account_info[
'ssl_fingerprint_sha256'] = self.ssl_fingerprint_sha256
self.notebook.set_current_page(4) # show fom page
elif cur_page == 4:
if self.is_form:
......@@ -3864,7 +3866,8 @@ class AccountCreationWizardWindow:
self.forward_button.set_sensitive(False)
self.notebook.set_current_page(4) # show form page
return
self.ssl_fingerprint = obj.ssl_fingerprint
self.ssl_fingerprint_sha1 = obj.ssl_fingerprint_sha1
self.ssl_fingerprint_sha256 = obj.ssl_fingerprint_sha256
self.ssl_cert = obj.ssl_cert
if obj.ssl_msg:
# An SSL warning occured, show it
......@@ -3878,8 +3881,9 @@ class AccountCreationWizardWindow:
'hostname': hostname, 'error': obj.ssl_msg})
if obj.errnum in (18, 27):
text = _('Add this certificate to the list of trusted '
'certificates.\nSHA1 fingerprint of the certificate:\n%s') \
% obj.ssl_fingerprint
'certificates.\nSHA1 fingerprint of the certificate:\n%s'
'\nSHA256 fingerprint of the certificate:\n%s') \
% (obj.ssl_fingerprint_sha1, obj.ssl_fingerprint_sha256)
self.xml.get_object('ssl_checkbutton').set_label(text)
else:
self.xml.get_object('ssl_checkbutton').set_no_show_all(True)
......
......@@ -5401,14 +5401,18 @@ Issued on: %(io)s
Expires on: %(eo)s
<b>Fingerprint</b>
SHA1 Fingerprint: %(sha1)s''') % {
SHA1 Fingerprint: %(sha1)s
SHA256 Fingerprint: %(sha256)s
''') % {
'scn': subject.commonName, 'sorg': subject.organizationName,
'sou': subject.organizationalUnitName,
'sn': cert.get_serial_number(), 'icn': issuer.commonName,
'iorg': issuer.organizationName,
'iou': issuer.organizationalUnitName,
'io': cert.get_notBefore(), 'eo': cert.get_notAfter(),
'sha1': cert.digest('sha1')})
'sha1': cert.digest('sha1'),
'sha256': cert.digest('sha256')})
self.set_transient_for(parent)
self.set_title(_('Certificate for account %s') % account)
......
......@@ -1299,7 +1299,7 @@ class Interface:
obj.exchange_items_list, obj.fjid)
def handle_event_ssl_error(self, obj):
# ('SSL_ERROR', account, (text, errnum, cert, sha1_fingerprint))
# ('SSL_ERROR', account, (text, errnum, cert, sha1_fingerprint, sha256_fingerprint))
account = obj.conn.name
server = gajim.config.get_per('accounts', account, 'hostname')
......@@ -1322,7 +1322,9 @@ class Interface:
f.write(obj.cert + '\n\n')
f.close()
gajim.config.set_per('accounts', account, 'ssl_fingerprint_sha1',
obj.fingerprint)
obj.fingerprint_sha1)
gajim.config.set_per('accounts', account, 'ssl_fingerprint_sha256',
obj.fingerprint_sha256)
if is_checked[1]:
ignore_ssl_errors = gajim.config.get_per('accounts', account,
'ignore_ssl_errors').split()
......@@ -1343,8 +1345,9 @@ class Interface:
'server?') % {'error': obj.error_text}
if obj.error_num in (18, 27):
checktext1 = _('Add this certificate to the list of trusted '
'certificates.\nSHA1 fingerprint of the certificate:\n%s') % \
obj.fingerprint
'certificates.\nSHA1 fingerprint of the certificate:\n%s'
'\nSHA256 fingerprint of the certificate:\n%s') % \
(obj.fingerprint_sha1, obj.fingerprint_sha256)
else:
checktext1 = ''
checktext2 = _('Ignore this error for this certificate.')
......@@ -1358,12 +1361,14 @@ class Interface:
_('SSL Certificate Verification for %s') % account)
def handle_event_fingerprint_error(self, obj):
# ('FINGERPRINT_ERROR', account, (new_fingerprint,))
# ('FINGERPRINT_ERROR', account, (new_fingerprint_sha1,new_fingerprint_sha256,))
account = obj.conn.name
def on_yes(is_checked):
del self.instances[account]['online_dialog']['fingerprint_error']
gajim.config.set_per('accounts', account, 'ssl_fingerprint_sha1',
obj.new_fingerprint)
obj.new_fingerprint_sha1)
gajim.config.set_per('accounts', account, 'ssl_fingerprint_sha256',
obj.new_fingerprint_sha256)
# Reset the ignored ssl errors
gajim.config.set_per('accounts', account, 'ignore_ssl_errors', '')
obj.conn.ssl_certificate_accepted()
......@@ -1376,11 +1381,16 @@ class Interface:
pritext = _('SSL certificate error')
sectext = _('It seems the SSL certificate of account %(account)s has '
'changed or your connection is being hacked.\nOld fingerprint: '
'%(old)s\nNew fingerprint: %(new)s\n\nDo you still want to connect '
'changed or your connection is being hacked.\n\nOld SHA-1 fingerprint: '
'%(old_sha1)s\nOld SHA-256 fingerprint: %(old_sha256)s\n\n'
'New SHA-1 fingerprint: %(new_sha1)s\nNew SHA-256 fingerprint: '
'%(new_sha256)s\n\nDo you still want to connect '
'and update the fingerprint of the certificate?') % \
{'account': account, 'old': gajim.config.get_per('accounts',
account, 'ssl_fingerprint_sha1'), 'new': obj.new_fingerprint}
{'account': account,
'old_sha1': gajim.config.get_per('accounts', account, 'ssl_fingerprint_sha1'),
'old_sha256': gajim.config.get_per('accounts', account, 'ssl_fingerprint_sha256'),
'new_sha1': obj.new_fingerprint_sha1,
'new_sha256': obj.new_fingerprint_sha256}
if 'fingerprint_error' in self.instances[account]['online_dialog']:
self.instances[account]['online_dialog']['fingerprint_error'].\
destroy()
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment