Você não pode definir valores diretamente para os parâmetros posicionais como este.
Você pode defini-las com o comando set , mas isso definirá todos os valores ( $1 , $2 , ...)
por exemplo,
$ set -- first second third fourth fifth
$ echo $1
first
$ echo $2
second
Agora existem dois casos em que $2 pode ser a string vazia; primeiro se nenhum valor tiver sido passado ou segundo se "" for passado como um argumento real e, portanto, ainda pode haver um $3 , $4 etc.
Podemos lidar com cada caso de uma maneira um pouco complicada:
#!/bin/bash
echo Before 1=$1 2=$2 3=$3 4=$4
if [ -z "$2" ]
then
first=$1
shift 2
set -- "$first" value "$@"
fi
echo After 1=$1 2=$2 3=$3 4=$4
O bit dentro do teste if garante que todos os outros valores sejam mantidos.
por exemplo,
% ./testing arg1 "" "arg 3" "and arg 4"
Before 1=arg1 2= 3=arg 3 4=and arg 4
After 1=arg1 2=value 3=arg 3 4=and arg 4
Mas você pode fazer coisas mais simples e usar apenas ${2:-value} , que será avaliado como value se $2 não estiver definido, então você não precisa se preocupar em reescrever os argumentos.