我有一个运行 Subversion 和 Mercurial 服务的 ssh 盒。连接到此盒时,脚本会验证用户是否仅运行 mercurial 或 svn 相关命令:
#!/bin/bash
#
# Verify that the requested command is an svnserve call.
#
# Note that sshd stores the command requested by the client in
# the variable "SSH_ORIGINAL_COMMAND".
echo $SSH_ORIGINAL_COMMAND | grep -E '^hg -R'
ISHG=$?
if [[ $SSH_ORIGINAL_COMMAND = "svnserve -t" || $ISHG -eq 0 ]]
then
exec $SSH_ORIGINAL_COMMAND
else
echo "You are only allowed svn access to this server."
fi
问题是,hg 验证不是很干净或安全。如果我在远程 ssh 命令中包含反引号,则“echo $SSH_ORIGINAL_COMMAND”行将顺利执行它。有人有什么建议可以稍微清理一下吗?
谢谢!
答案1
是的。不要使用 shell。用一种语言编写一个程序,确保它要执行的二进制文件都是白名单中的。
答案2
Mercurial 附带了一个专门用于此目的的工具!使用contrib/hg-ssh
我们提供的脚本用于限制命令。该文件包含此标头以解释如何使用它:
~/.ssh/authorized_keys
要与该选项一起使用command
,请参阅 sshd(8):command="hg-ssh path/to/repo1 /path/to/repo2 ~/repo3 ~user/repo4" ssh-dss ...
(可能与这些其他有用的选项一起:
no-port-forwarding
,,no-X11-forwarding
)no-agent-forwarding
这允许通过 SSH 从/向作为参数指定的存储库进行拉取/推送。如果您的所有存储库都是公共目录的子目录,则可以使用以下方法允许更短的路径:
command="cd path/to/my/repositories && hg-ssh repo1 subdir/repo2"
您可以使用普通 shell 的模式匹配,例如:
command="cd repos && hg-ssh user/thomas/* projects/{mercurial,foo}"