我有一组服务器,每个服务器的配置文件当前包含敏感、关键任务系统(消息队列、数据存储和其他服务)的纯文本密码。
有些人将关键密码从配置文件移到运行服务器进程的用户帐户的环境变量中。这样,配置文件就可以提交到版本控制中,系统管理员只需在设置服务器系统时创建适当的环境变量即可。当然,对运行这些服务的帐户的访问受到严格限制。
这真的是避免在纯文本配置文件中使用密码的最佳方法吗?或者有更好的方法吗?
答案1
如果您使用的是 Linux 系统,请查看 /proc/*/environ 并确定环境变量是否是存储敏感信息的好地方。/proc/self 是当前进程:
$ tr '\0' '\n' < /proc/self/environ
USER=me
LOGNAME=me
HOME=/home/me
PATH=/usr/bin:/bin:/usr/sbin:/sbin
MAIL=/var/mail/me
SHELL=/usr/bin/sh
SSH_CLIENT=1.2.3.4 58195 22
SSH_CONNECTION=1.2.3.4 58195 7.8.9.0 22
SSH_TTY=/dev/pts/1
TERM=xterm
不用担心,设置环境变量的东西可能正在某处读取文件。
要记住的是,使用密码意味着该密码可供程序使用。如果此密码不是由用户在程序需要时输入的,则该密码必须仅基于程序的访问权限才可访问。您可以在本地加密密码,并让程序使用密钥解密,但这样做只会隐藏密码以防止意外泄露;具有与程序相同访问权限的人可以执行与程序相同的操作,包括读取加密密钥。
正确的做法是让应用程序以受限帐户运行,并将密码存储在受文件系统级权限保护的文件中。希望您可以“包含”文件或类似文件,以使密码不受版本控制系统的保护(假设 VCS 没有安全控制)。为了防止无意泄露,请以您想要的任何方式隐藏密码 - 使用 base64 编码,使用 pgp 加密,无论服务器程序的选项集如何合理。如果您正在编写一个程序来执行此操作,您能做的最好的事情就是仅在需要时提示用户输入密码,然后在使用密码后立即从内存中清除该密码。
答案2
最后,如果你有任何需要读也书面,你最终会用密码来保护一些东西(或者如果你真的您可能很担心,因为您使用的是物理硬件智能卡和 PIN,无论您使用了多少层加密。
这归结为系统安全性与便利性之间的基本问题。您可以通过设置很多很多层安全控制来增加“纵深防御”,恶意行为者必须突破这些控制才能获得“商品”,但当合法行为者想要读取或更改某些数据时,他们必须经过一系列的考验。另一种方法是将明文密码保存在文本文件中。
如果我真的想保护关键任务系统中的某些信息,我会怎么做:
使用全盘加密,以便整个持久存储的内容都被加密。
限制对机器的物理访问。使用安全锁定机制锁定机器底盘并控制对钥匙的物理访问。雇佣武警(武装警卫)作为门卫。
在设备的操作系统中强制实施细粒度的强制访问控制 (MAC)。您可以从 GNU/Linux 上的 SELinux 之类的东西开始,并将其设置为强制执行,然后根据生产软件的确切需求定制策略,允许这些帐户精确(且仅)获得他们需要的文件的权限。
如果您要使用系统专用密码和配置文件版本控制,您确实需要避免将明文密码错误地提交到版本控制中,因为从 VCS 的缓存中删除泄露的密码可能很困难。环境变量是解决此问题的几种可行方法之一。另一种方法是在程序启动时提示输入密码,但随后重新启动机器并恢复运行状态需要手动操作,无法自动完成,因此再次存在便利性和安全性之间的矛盾。
确保有网络专家随时负责防火墙权限,以尽量减少网络攻击的风险。审核(渗透测试以及白盒测试代码)任何与外部系统(尤其是公共互联网)交互的软件。“接口”不仅包括直接网络连接,还包括读取或写入“不受信任”的数据(其字节来自安全服务器的 RAM/磁盘/CPU 之外的数据)。
这不是一个完整的列表,但第 4 点可能特别与您相关,但如果您至少不执行第 1 步到第 3 步,考虑第 4 点和第 5 点对您没有太大帮助,因为您的系统在相当基本的层面上并不安全。
答案3
在环境变量中传递密码与让程序从文件中读取密码一样安全。只有以同一用户身份运行的进程才可以读取进程的环境,并且无论如何这些进程都可以读取相同的文件。
请注意,这与在命令行上传递密码不同。命令行参数可由同一台计算机上运行的所有进程读取(除非采取强化措施),而不仅仅是以同一用户身份运行的进程。
如果您通过环境传递变量,请注意程序是否启动了其他程序。那些其他程序将继承其父程序的环境。因此,如果您担心其他程序可能会意外泄露其环境的内容,请不要这样做。
您的方案中的缺陷是“在设置服务器系统时创建适当的环境变量”。环境变量是进程的动态属性。您无法在设置系统时创建它,如果您所说的设置是指重启后仍然存在的东西。您的意思是管理员安排此变量在某个用户登录时出现在环境中。这是通过配置文件(通常是~/.pam_environment
或~/.profile
或从中读取的文件~/.profile
)完成的。因此,此解决方案实际上并没有将密码移出配置文件。
将密码置于用户登录时环境中的做法并不是一个好主意。这意味着以该用户身份运行的每个进程都会拥有这个秘密,因此它很容易在任何地方泄露。
密码应放在受版本控制的配置文件和正常部署机制之外的文件中。如果方便的话,可以在某个时候将密码放在环境中,但应尽可能少地设置程序。