SSL vs TLS vs STARTTLS

翻译者:易建科技基础架构中心研发经理张冬卯

SSL vs TLS vs STARTTLS

SSL, TLS和STARTTLS都是在计算机安全里面, 都很容易让人混淆的词.

SSL和TLS都提供了加密2台计算机(如服务器和客户端)之间通信的办法. TLS是SSL的继任者, 所以除非提到具体协议的版本,TLS和SSL这2个词是可以混用的, 在大多数情况下的意思相近.

STARTTLS是一种把已经存在的一条不安全的链接, 用SSL/TLS的加密方法, 把这条不安全的连接升级成安全的连接. 注意, 尽管STARTTLS里面只有"TLS", 但是你既可以用TLS也可以用SSL.

SSL/TLS的版本号

由于历史原因, SSL和TLS之间的版本号顺序并不一致, 当TLS代替SSL作为下一代的加密标准时, TLS采用了新的版本号, 并且

新的版本号下面还有小版本号. 所以按照时间顺序, SSL/TLS的软件版本序号从最老到最新的顺序应该是: SSL v2, SSL v3, TLS v1.0, TLS v1.1, TLS v1.2, TLS v1.3

[译注: 比如我用chrome连接知乎的443端口, 看到的是TLS v1.2加密]

SSL vs TLS vs STARTTLS_第1张图片

当客户端连接到一个SSL/TLS加密的端口, 或者用STARTTLS升级当前连接时, 通信双方根据双方软件的配置, 做自动协商, 选择某一种SSL/TLS做加密通信.

大量的软件都已经默认支持SSL/TLS[译注: 如浏览器, 邮件客户端, HTTP服务器]. SSL v2早已再多年前由于存在安全漏洞弃之不用. SSL v3也由于有安全漏洞不再使用. 几乎所有软件都支持TLS v1.0. 在2016年10月, TLS v1.1 和 TLS v.2 也已经被广泛的支持.

尽管IE对TLS支持有一些例外.

总有软件搞混TLS和STARTTLS

一个让事情更加复杂的因素是一些邮件客户端也会搞混这2个名词.当他们应该用STARTTLS这个词时, 但他们却错误地用成了TLS.

比如,老版本的Thunderbird里面的选项"TLS"表达的意思是"强制使用STARTTLS升级当前连接, 如果协商失败, 返回连接失败". 另外一个选项

"TLS, if availiable"表达的是"如果服务器支持STARTTLS, 那么就用STARTTLS通信, 如果服务器不支持STARTTLS,那就不安全连接"

SSL/TLS 和STARTTLS的端口

为了增强已有的邮件协议(如IMAP, POP)的安全性, 但是并不破坏原有协议, 协议工程师的做法再是原有协议不变的基础上, 在邮件协议下方增加一个SSL/TLS的传输加密层. 但是为了区分这个协议是明文的邮件协议还是加密的邮件协议, 每种邮件协议都增加了一个额外的端口来传输加密的数据. 所以:

IMAP协议默认端口 143, SSL/TLS 加密的IMAP的默认端口是993

POP 协议默认端口110, SSL/TLS 加密的POP的默认端口是995

SMTP协议默认端口25, SSL/TLS加密的SMTP的默认端口是465

从某种角度看, 每种邮件协议占据2个端口是一种浪费. 所以, 出现了一个解决办法, 你可以只需要使用一个端口.通过普通端口生成的连接起初是不加密的, 但是双方可以通过STARTTLS协议把这个非加密连接升级成加密连接.

上面每种邮件协议都加入了新的协商机制, 邮件服务器告诉客户端当前的明文协议支持升级成加密的连接.在当前连接升级到加密连接之前, 不要做登录操作(传输用户名和密码). 在实现不完整的邮件客户端中, 会出现下面2种错误的处理方法:

一些邮件客户端忽略了服务器表达的"直到升级到加密连接前, 不要发登录密码", 还是尝试登录, 用明文发送用户名和密码. 即使服务器拒绝了这个明文登录, 但是用户名/密码还是已经泄露到互联网中

另一些邮件客户端看到了"直到升级到加密连接前, 不要发登录密码"这个声明. 但它不自动升级当前连接, 而是直接向用户报告登录失败

上面这2个问题引发了现存的邮件客户端广泛的兼容性问题, 所有大多数系统管理员仍然使用双端口的解决方案, 一个端口传输明文协议, 另一个端口传输加密数据.

由于2个端口很容易让客户混淆, 很多邮件服务商采用了一刀切的办法, POP和IMAP协议只保留加密端口, 现在这个配置变成了目前的事实标准. 很多网站禁用了明文传输端口(IMAP的143和POP的110), 强制用户使用加密连接. 由于不再存在明文端口, 这些邮件网站也不再支持STARTTLS协议.

SMTP的STARTTLS是一个例外

[译注: 上文只说很多网站的POP和IMAP协议只支持加密端口, 但是SMTP仍然支持非加密端口]

一个例外是SMTP协议. 很多网站还支持非加密端口的SMTP是另一个原因. 大部分邮件客户端用SMTP协议在端口25提交邮件. 但是SMTP协议最初设计在MTA之前传输邮件.所以新的端口587被rfc定义用来提交邮件.

尽管新端口587没有强制用户使用STARTTLS, 但是随着邮件客户端和邮件服务器之前的安全通信的重要性越来越高, 端口587也变得越来越流行. 所以, smtp的SSL/TLS端口465也被标准回收, 推动用户迁移到新端口587上用STARTTLS协议做加密传输.

结果是在大多数情况下, 邮件系统允许普通用户从端口587通过STARTTLS协议提交邮件(用户安全的提交用户名密码). 通过把邮件提交任务从端口25迁移走, 运行商现在可以封锁所有普通用户25端口, 通常端口25也是垃圾邮件的来源.

不幸的是, 修改SMTP的默认端口的缺点是, 存在大量的邮件客户端, 他们只支持在端口465上的SSL/TLS, 不支持在端口587上的STARTTLS.但是邮件客户端的更新很慢, 所有邮件运营商为了兼容性考虑, 都不会移除端口465.

目前, SMTP的情况是这样, 一些人使用STARTTLS在端口587上登录服务器, 另一些人在端口465用SSL/TLS登录邮件服务器.

[译注: 但一些国内的情况更糟, 一些邮件运营商仍然没有用标准的587端口, 而仍然沿用25端口, 这时候需要用STARTTLS在25端口上登录服务器]

========翻译完========

以上就是我们写登录SMTP服务器代码时注意事项, 一定要知道SMTP的打开的端口是SSL/TLS端口还是明文的需要升级的STARTTLS端口,

然后还要知道Auth的方式, 比如PLAIN AUTH还是LOGIN AUTH等等, 要把这些排列组合才可以正确的发邮件.

用golang表示的代码例子:

用STARTTLS连接SMTP服务器

https://gist.github.com/jim3ma/b5c9edeac77ac92157f8f8affa290f45gist.github.com

直接用SSL/TLS连接SMTP服务器

https://gist.github.com/chrisgillis/10888032gist.github.com

由于golang标准库smtp不支持Login Auth, 需要自己加入新的Auth才可以登录smtp服务器:

https://gist.github.com/andelf/5118732gist.github.com

此外还有如果用TLS连接SMTP服务器, 有时候会发现报错:

panic: x509: certificate is valid for XXX

这是说明邮件的证书没有被ROOT CA认证, 当然和你无关, 解决办法是再tlsconfig里面加一个选项InsecureSkipVerify:

tlsconfig := &tls.Config{ ServerName:host, InsecureSkipVerify:true }

你可能感兴趣的:(SSL vs TLS vs STARTTLS)