网易所谓的“EAL 3+”证书是个什么东西?

今天一早,乌云上曝出了网易邮箱的安全问题,过亿的用户信息被泄漏。而网易方面也是反应神速,一份宣传稿发到各大媒体,说是自己家的邮箱不仅没问题,而且安全性方面还是全国最牛X的。公告原文如下(摘自新浪):

文中提到了一个 EAL 3+ 的认证,而且号称是国内最高等级。这个到底是什么呢?我们来研究一下。

网易的企业邮箱网站在今年 8 月底发布了一则新闻,说是企业邮箱系统获得了 EAL 3+ 认证,还有一个像模像样的证书。图片就不贴了,大家点链接进去看吧。证书大意是“网易企业级邮箱系统”获得 中国信息安全评测中心信息安全实验室 颁发的 EAL 3+ 证书。

首先,这个系统的名字有歧义,企业级的邮箱系统,不一定只是给企业用的。网易可以说自家的免费邮箱也做到了企业级的安全性。当然网易算是心虚,没有在自己的首页发表这么个新闻,只是在企业邮箱的网站上发了。那我们只能认为只有网易的企业邮箱获得了这个证书,而大众所使用的免费邮箱却没有。而乌云提到的过亿的用户信息,显然不是从企业邮箱来的。网易在公告中宣称的“国内最安全”,只不过是偷换概念罢了。

当然,不能排除网易内部实际上使用的是同一套系统,即企业邮箱和免费邮箱的后台是一样的,只是页面看上去不一样。那么企业邮箱获得了安全认证,免费邮箱也就同样安全。好吧,然后我又去看了一下 EAL 3+ 的实际内容。

EAL(Evaluation Assurance Level)是某个国际组织设立的标准,按它的实际操作来看,每个国家都可以设立自己的评测实验室,对本国的软件进行评测。中国、美国、英国、法国、西班牙等国都有自己的评测实验室。中国的评测由上面提到的 中国信息安全评测中心信息安全实验室 来进行。在中国信息安全评测中心的网站上,可以找到中文版的 EAL 1 - 5 的评测细节,其中这个链接指向的是 EAL 3 的指南(PDF)。文档我稍微看了一下,实际它只有 20 页不到,大约就是一个对文档细节的约束。其中对于测试文档的要求,只有半页,还没我的一篇博文长。摘录如下:

基本上它就是要求了测试文档的完整性,对于要测哪些方面、具体测试的实施以及测试的结果,通通没有要求。也就是说,只要文档写得好,通过 EAL 评测并不难。而做过产品的同学们都知道,文档和最终产品的差距还是相当大的。举个例子:

另外,网易的证书上还提到了评测方法:GB/T 30270-2013 信息技术 安全技术 信息技术安全性评估方法。我搜索了一下,这个《方法》没有电子版,只有纸制书籍出售,当当网的卖价是 103 元。我自然不会为了写博客还去买本破书,因为当当的介绍中提到,这本书只有 200 多页,目录显示它的内容就是 EAL1 到 EAL5 的实际内容,外加一些前言备注什么的。大致可以看到,书中没有额外的内容,具体的评测和上面给出的 PDF 链接没有两样。

所以实际上,网易获得了证书 和 系统的安全性 这两件事并没有直接联系。而即使是网易获得证书的企业邮箱,它的安全性也令人堪忧:

上图中,即使我选择了“全程使用 SSL”,登录页面也没有使用 SSL。在登录页面不使用 SSL 的情况下,即使登录接口使用了 SSL 也是形同虚设的,因为未加密的登录页面可能被劫持,只需要添加一段脚本,就可以神不知鬼不觉得拿到帐号信息。详细的分析我曾经在乌云看过一篇文章,一下子找不到了,等找到了再补上。

对于那些担心自己密码失窃的同学们,我只能建议一句:保护个人信息,远离网易。当然,如果你在其它网站使用了和网易一样的密码,请立即修改。

感谢国家

好久没写文章了,最近这段时间公司事务繁忙,好不容易有点闲暇时间了,就跑过来照顾一下博客。

前几天 StrongVPN 的客服联系了我,问我要 Paypal 的帐号以便付款。他家前段时间升级了代理系统,可能是把我的 Paypal 记录弄丢了,于是我写信回了过去,也顺便去看了一下,我将收到多少钱。

不看没关系,一看吓了一跳,佣金居然有四位数?然后看了一下详细数据,确定了是新系统才有的记录,不是历史数据。敢情在这两个月里网络环境如此地恶劣,大家一起上 VPN 的节奏。

感谢国家,下个月收到佣金可以换个 iPhone 6s 了。

顺便做个广告,StrongVPN 更新了他们的服务,现在更注重隐私,并且提到了无限流量的 VPN,要体验一下的同学点这里

写于博客密码泄露之后

很不幸我的博客密码被盗了,一个不名黑客在半夜入侵了我的主机,植入了菜刀,远程控制了机器。然后他窃取了一些重要资料(比如一些羞羞照),并且把主机变成了一台肉机。我发现的时候,肉机已经偷跑了超过 5000 美元的流量......

在电脑手机前偷笑的各位可以稍微停一下了。以上只是我被害妄想症的一种表现,它实际上并没有发生。

由于对安全的偏执,我假想了各种安全漏洞的情形,然后加以防御。之前讨论过 WordPress 的密码安全性插件安全性,这次来探讨一下密码失窃之后,有哪些亡羊补牢的方法。

假设一名黑客偷取了本博客的管理员密码,(先假设只是博客的密码,而不是主机的管理员权限),那么他能做哪些事情?

一,很明显,他可以操作博客的数据库,新建用户、新建文章、删除文章等。

二,黑客可以在后台直接挂马,然后进行更强大的远程操作。

对于第一条,似乎没有特别好的方法,一旦密码被盗,数据库就只能放弃了。当然,如果你的博客没有任何加密的内容,数据库被盗也没什么好怕的,本来就都是公开的东西。

接下来重点说一下第二条。

PHP 有一个很好用也很危险的特性,就是源代码可以直接执行;而 WordPress 也有一个很好的特性,即可以在后台直接修改插件代码。于是一旦黑客控制了后台,他可以在源代码里嵌入一行如下的语句,然后就可以远程控制了。对,PHP 就是那么强大。

要防止这种情况,最有效的方法是在把所有源代码设置为只读,即 Linux 文件属性 400(或 444),这样可以避免任何人对文件进行修改。但这样做之后,自己真想要修改文件的时候,却是非常麻烦,先要 SSH 登录,把文件属性设为可写(如 755),然后再回到后台改文件。另外,这样做也阻止了 WordPress 的自动更新,一定程度上降低了安全性。

对此, WordPress 提供了一个简单的防御方式,可以 wp-config.php 中添加一行:

这样可以禁用掉 WordPress 中修改源代码的界面,包括插件和主题,同时也禁止了安装新的插件和主题。当然这样同样会有上述的问题,即每次修改文件之前,需要先修改 wp-config.php。为了避免对 wp-config.php 的频繁修改,我们可以加一点小小的逻辑,如下:

它的含义是在不是运行 WP Cron 并且 Session 中没有定义 enable_edit 的时候,才禁用对主题和插件的修改。开启 WP Cron 的原因是它会定期检查并更新 WordPress,而 Session 的定义则可以按需开启修改的界面。

手动启用修改界面,还需要一段代码,写在 functions.php 中:

然后访问 http://你的博客地址/wp-admin/admin-ajax.php?action=temp_enable_edit 即可临时开启对插件和主题的修改,有效期到 Session 过期为止。需要注意的是,并不所有的主机都启用了 Session。如果你的主机把 Session 关了,你可以改成使用 Cookie,效果类似。

这种方法是安全和易用的一个折中,它假设了 WordPress 不会有 Bug,比如 DISALLOW_FILE_MODS 工作正常,并且没有安装可以直接运行 PHP 代码的插件

另外还有一些其它的方法仅供参考:

  • 给 wp-admin/ 文件夹加一个密码,比如 Apache 的 Basic Authentication。我觉得每次登录都需要多输一个密码,实在太麻烦了。
  • 重命名 wp-admin/ 文件夹让别人找不到。根据前几年的讨论贴,这种方法并不能完美工作,也就说是 WordPress 的代码某种程度上依赖于 wp-admin 而不能改名。
  • 创建一个新的域名,只用来访问 wp-admin,而原先的域名供访客浏览。这种方法的前提是你愿意支付双倍的 SSL 证书费用。

这个世界上没有绝对的安全,只不持之以恒的防御。

如何生成 CSR 文件

CSR,Certificate Signing Request,是制作 SSL 证书的必要步骤。一个 CSR 文件中描述了 SSL 证书持有人的信息(如个人姓名或公司名称)、联系地址等,用于验证 SSL 证书和域名是同一个人持有,以确保网站的合法性。

在 Linux 上生成 CSR 文件通常需要用到 OpenSSL 工具,这是一个命令行工具,参数一大堆,对于偶尔用一下的用户来说,可能不太友好。于是 DigiCert 提供了一个在线工具,用于生成 OpenSSL 的命令行,然后再拿去网站主机上运行就可以了。理论上 OpenSSL 一定要在网站所处的主机上运行,即换了主机之后要重新制作一个新的证书,但实践中并不强制这一步骤。

工具截图如下:

示例中我填写了 Google 的信息,请按实际情况修改,各项的含义如下:

  • Common Name: 你的网站域名
    • 如果你购买的是单一域名的 SSL 证名,请填写实际用到的域名,如 leonax.net 或者 www.leonax.net;在 DigiCert 购买的单一域名,填写 www 版本送裸域;
    • 如果购买的是野卡,则填写 *.leonax.net;
  • Organization: 公司名称,如果是个人用户,请填写自己的全名;
  • Department: 部门名称,可不填;
  • City: 所在城市;
  • State / Province: 所在州/省;
  • Country: 所在国家;
  • Key Size: 加密字长,目前常用的是 2048,如果对安全性要求较高,可以选择 4096;

全部填好之后,点击“Generate”即可以生成命令行,把右侧生成出来的一串命令,复制到 Linux 主机上运行即得到一个 CSR 文件。

之后要做的步骤是向 SSL 证书提供商上传这个文件,以获得最终的 SSL 证书,之后再详述。

注:OpenSSL 是一个 Linux 的工具,如果你的主机所用的是 Windows 或其它操作系统,可以在这个页面找到相应的介绍。

HHVM 中的 RepoAuthoritative 模式

HHVM 3.8 中提出了一个 RepoAuthoritative 模式,用于提升 PHP 代码的效率。

PHP 代码是解释型的,也就是每次执行的时候,PHP 引擎都会读取源代码,编译成机器代码之后再执行。这也就是为什么解释型语言比较慢的原因之一,它不能一次编译完成,而是一定要运行到哪里编译到哪里。编译的过程拖慢了整个运行的效率。而这样每次“编译”的过程显得有些多余,因为代码是基本不会变的。于是 PHP-FPM 是提出了 OpCache 来缓存编译的结果,如果代码已经被编译过,且源代码没有改动,则继续使用缓存。

而 HHVM 则更进了一步,在 RepoAuthoritative 开启之后,指定的文件夹会被编译成一个二进制文件,并同时进行优化。官方说法是,这样的优化可以在 HHVM 本身的基础上,再提升 20% 的运行效率。

开启的方法如下,其中 /var/www 是想要编译的文件夹。

关闭的方法如下:

编译的过程使用了 /var/run 做为临时文件夹,实测 WordPress 编译完成之后,要占用 175MB 的空间,如果 /var/run 太小会提示“disk is full”错误。

当然, RepoAuthoritative 也有一定的限制,比如不能使用 eval() 和 create_function() 等动态改变代码的语句。不过 WordPress 中几乎没有用到,说“几乎”是因为实际上有两处用到了,一个是在 wp-includes/pomo/po.php 中,这个文件貌似根本不会被执行到;另一处是在 wp-includes/atomlib.php 中,只要不使用 atom 作为 RSS feed 即可。另外就是编译完成之后,源代码的改动就会“失效”,要再一次编译才会使改动起作用。

然而,由于 HHVM 自身已经相当地高效了,开启 RepoAuthoritative 模式之后没有明显的变化。本站实测下来,TTFB 时间大概减少了 50ms,对于原本只有 700ms 左右的速度来说,看不出效果。我试用了一下之后就把它关闭了。不过至少说明在 WordPress 上使用这个功能是没有问题的。如果你的 WordPress 中有非常慢的功能,不妨试一下 RepoAuthoritative 模式。

在 PHP 中实现 String 的 StartsWith 和 EndsWith

和 Javascript 一样,PHP 中也没有对 String 实现 StartsWith 和 EndsWith 这两个方法。由于这两个方法很常用,我们只好自己来实现一下。

在 PHP 4 中,常见的做法和 Javascript 类似,如下:

上面的方法会使用更多的内存,并且对字符串扫描了两遍,效率不高。这种方法在 PHP 5 中已经过时了,因为 PHP 5 给出了一个 substr_compare 方法,可以直接比较子字符串,如果代码就可以简化成这样:

上述实现的效率至少快了一倍。由于历史遗留的问题,很多现存代码都没有更新,比如 WordPress 的源码中就存在了老版本的实现。如果你已经在使用 PHP 5 或者 HHVM,不妨试试第二种实现。

全站 CDN 开放测试

几个星期之前本站开始使用了 KeyCDN 作为内容分发和加速,和其它多数 CDN 一样,KeyCDN 也是可以被用于全站 CDN 的。只不过由于 WordPress 自身的一些缺陷,使得全站 CDN 配置起来非常麻烦。

全站 CDN 的好处不言而喻,就是速度快。本站的主机在台湾,亚洲的读者可能没什么大问题,但从欧洲访问过去,最快也至少要 500ms 才能得到内容(第一字节时间,TTFB)。而使用了 CDN 之后,TTFB 会下降到 50ms 以下,必要的 CSS 文件在 500ms 内下载完毕,达到了真正的秒开。

于此同时,之前的一些问题,比如留言之后 CDN 刷新不及时,都已经修复。目前已经没有已知的阻碍正常阅读的使用问题了。想体验一下的同学,可以在左上角目录中选择“使用 CDN”。如果你没有看到这个链接,则说明要么你已经在使用 CDN 了;要么,本站的 CDN 已被墙。

节点分布图可以看出,离大陆最近的节点在香港,除了主机所在地台湾之外,各大主要网络区域都有节点覆盖。也就是说,除了来自台湾的读者可能感受不到 CDN 的优势之外,世界上大多数地区的读者的访问速度都会有提升。

由于 KeyCDN 并不是针对全站 CDN 来设计,它使用起来或多或少还是有些不方便,没有 CloudFlare 那样的完美。但作为一个每月只需要不到一美元的服务,KeyCDN 真是物超所值。继续测试一段时间之后,如果没有太大的问题,站点将全面切换至 CDN 模式,进一步保护主机的安全。