【发布时间】:2015-08-08 18:11:06
【问题描述】:
在bash shell 中,可以使用declare -p 轻松引用数组,然后稍后使用evaled 将它们恢复正常。对于通过 SSH 将数组(作为脚本的一部分)传递到远程计算机,这似乎是可以接受的。
问题是,相反,我不希望得到同样程度的信任。如果远程机器受到攻击,感染可能会通过未经处理的eval 语句传播到本地机器。
目前,为了在机器之间传递数组,我使用这样的方法:
#!/bin/bash
# Define the modules we expect to find installed on the remote machine
expected_modules=(foo-module bar 'baz 2.0')
# SSH into the remote machine, send the arrays back and forth with "declare -p"
unparsed_missing_modules=$(ssh remote-machine /bin/bash << EOF
check_for_module() {
# Placeholder so that this can be tested locally
case \$1 in
foo*) true;;
*) false;;
esac
}
$(declare -p expected_modules)
missing_modules=()
for module in "\${expected_modules[@]}"; do
if ! check_for_module "\$module"; then
missing_modules+=( "\$module" )
fi
done
declare -p missing_modules
EOF
)
# Unpack the result (this is what I want to find an alternative to)
eval "$unparsed_missing_modules"
# Do something with the result after unpacking into an array
for module in "${missing_modules[@]}"; do
echo "Warning: Remote machine is missing $module" >&2
done
当ssh 会话的输出直接传递给eval 时,此脚本中的主要不安全因素已接近尾声。如何清理bash 中的此输入?
【问题讨论】:
-
假设没有预期的模块在其名称中包含换行符是否安全?如果是这样,我就不会费心尝试在任一方向上对数组进行编码;只需使用模块名称的多行列表即可。
-
顺便说一句,您最好使用
<<'EOF'来逐字传递脚本,并在远程shell 的命令行中逐字传递参数,而不是将它们替换为脚本文本;本地计算机上的数据扩展为远程代码的空间更少。 -
...我在回答中展示的一种技术。 :)
-
@chepner,当然,这可能是安全的(从安全角度来看肯定是安全的),但是由于没有保证有效数据范围的人可能会重复使用该问题,为什么不这样做是否正确并涵盖了所有有效的 C 字符串?
-
我不想写一个完全正确的答案(我很确定我会弄错一些细节),所以我只是想提出一个更容易实现的替代方案。另外,我很确定你很快就会提供正确的答案:)
标签: arrays linux bash shell ssh