fishbone
fishbone

Reputation: 3259

Prevent directory traversal vulnerability in bash script

How can I prevent directory traversal attacks in a bash script, where arguments contain directory names?

Example:

$STAGE=$1
$APP=$2
deploy.sh dist/ /opt/apps/"$STAGE"/"$APP"

The $STAGE and $APP variables are set from outside. An attacker could change this to an arbitrary path with "..".

I know the usual solution is to compare the directory string with the result of a function that returns the absolute path. But I couldn't find a ready solution and don't want to come up with my own.

Upvotes: 3

Views: 1416

Answers (2)

jschnasse
jschnasse

Reputation: 9588

Something like this?

#! /bin/bash

STAGE=$1
APP=$2

expectedParentDir="/opt/apps/"

function testDir(){
  arg=$1
  if [[ ! -f $arg ]]
  then
      echo "File $arg does not exist."
      exit 1
  fi
  rpath=$(realpath $arg)
  if [[ $rpath != ${expectedParentDir}* ]]
  then
   echo "Please only reference files under $expectedParentDir directory."   
   exit 2
  fi
}

testDir /opt/apps/"$STAGE"/"$APP"

... deploy ...

Example Call

test.sh "../../etc/" "passwd"
Please only reference files under /opt/apps/ directory.
------------
test.sh "../../etc/" "secret"
File /opt/apps/../../etc//secret does not exist.
  1. Test existence of file with -f or use -d if target must be a directory
  2. Use realpath to resolve path
  3. Use == ${expectedParentDir}* to find out if resolved path starts with expected string

Upvotes: 1

mti2935
mti2935

Reputation: 12027

The script should be run as a user that only has permissions to access the necessary directories.

Upvotes: -1

Related Questions