环境变量污染本质是不该暴露的值被设为全局可见、不该继承的路径被加入关键变量或本应隔离的上下文混入高权限执行链,解决核心是控源、限域、验值、清冗——即区分变量类型控制导出、按需限定作用域、重置可信path并清除ld_preload等高危变量、运行前校验存在性与权限。
环境变量污染系统,本质是不该暴露的值被设为全局可见、不该继承的路径被加入关键变量、或本应隔离的上下文混入了高权限执行链。解决核心不是“多设”,而是“控源、限域、验值、清冗”。
控制源头:区分变量类型,避免无意识导出
shell变量默认只在当前进程有效,export之后才变成子进程可继承的环境变量。很多污染源于把配置项、临时路径甚至密码直接 export。
- 定义时用普通赋值:
CONFIG_PATH="/etc/myapp"(仅当前脚本可用) - 导出前确认必要性:
export CONFIG_PATH仅当curl、python等子命令真需要读取它时才执行 - 检查是否已导出:
env | grep CONFIG_PATH或printenv CONFIG_PATH,发现意外存在就用unset CONFIG_PATH
限制作用域:按需设置,不越界生效
全局配置影响所有用户和服务,错误添加可能让攻击者通过任意用户会话劫持PATH或LD_PRELOAD。
- 用户级变量写入
~/.bashrc或~/.profile,不碰/etc/profile等系统文件 - 服务专用变量,优先用 systemd 的
Environment=和UnsetEnvironment=显式声明,不依赖登录环境 - 容器内运行时,用
ENV指令或--env-file加载,禁止source /etc/profile
清理高危路径:重置 PATH 与清除加载类变量
PATH、LD_PRELOAD、PYTHONPATH 是最常被利用的污染入口。启动脚本第一行就该做“环境消毒”。
在 Windows 上执行终端命令,或对比 Windows 与 Linux 的 Shell 语法时使用。建议先检测当前 Shell 是 PowerShell 还是 cmd.exe,再给出相应命令……
- 重置 PATH:
PATH="/usr/bin:/bin:/usr/sbin:/sbin"(显式列出可信路径,不拼接 $PATH) - 清除动态加载变量:
unset LD_PRELOAD LD_LIBRARY_PATH PYTHONPATH PERL5LIB - 调用命令优先用绝对路径:
/bin/cp而非cp;或先校验:command -v cp >/dev/null || exit 1
运行时校验:对关键变量做合法性检查
静态配置防不住运行时篡改。对 PATH、HOME、JAVA_HOME 等变量,应在脚本关键逻辑前做三重验证。
- 存在性:
[ -d "$JAVA_HOME" ] || { echo "JAVA_HOME missing"; exit 1; } - 权限合规:
ls -ld "$JAVA_HOME" | awk '$3 != "root" || $1 !~ /^d.r.xr-xr-x$/ {exit 1}' - 内容可信:检查目录下是否存在可疑二进制(如名称含
inject、hack、tmp)
不复杂但容易忽略










