Why should eval be avoided in Bash, and what should I use instead?

前端 未结 2 1986
傲寒
傲寒 2020-11-21 22:53

Time and time again, I see Bash answers on Stack Overflow using eval and the answers get bashed, pun intended, for the use of such an \"evil\" construct. Why is

2条回答
  •  北荒
    北荒 (楼主)
    2020-11-21 23:29

    How to make eval safe

    eval can be safely used - but all of its arguments need to be quoted first. Here's how:

    This function which will do it for you:

    function token_quote {
      local quoted=()
      for token; do
        quoted+=( "$(printf '%q' "$token")" )
      done
      printf '%s\n' "${quoted[*]}"
    }
    

    Example usage:

    Given some untrusted user input:

    % input="Trying to hack you; date"
    

    Construct a command to eval:

    % cmd=(echo "User gave:" "$input")
    

    Eval it, with seemingly correct quoting:

    % eval "$(echo "${cmd[@]}")"
    User gave: Trying to hack you
    Thu Sep 27 20:41:31 +07 2018
    

    Note you were hacked. date was executed rather than being printed literally.

    Instead with token_quote():

    % eval "$(token_quote "${cmd[@]}")"
    User gave: Trying to hack you; date
    %
    

    eval isn't evil - it's just misunderstood :)

提交回复
热议问题