caller — returns the context of any active subroutine call

$cat test.bash
!/bin/bash
die() { local frame=0 while caller $frame; do ((frame++)); done echo "$*" exit 1 }
f1() { die "*** an error occured ***"; } f2() { f1; } f3() { f2; }
f3 $

$bash test.bash 
12 f1 test.bash
13 f2 test.bash
14 f3 test.bash
16 main test.bash
*** an error occured ***
$chmod +x test.bash
$./test.bash 
12 f1 ./test.bash
13 f2 ./test.bash
14 f3 ./test.bash
16 main ./test.bash
*** an error occured ***
$