2

I'm trying to understand if there are any benefits of using:

pushd my_dir
make all  # ... or something else
popd

vs

(
    cd my_dir
    make all  # ... or something else
)

or is it merely a preference thing?

I guess the latter notation can have issues like you may need to set -e (and other flags again), but it still carries out the exit code of its last command, and looks better in terms of syntax.

3
  • cd is a standard command, pushd and popd are bash things, so they would not be portable unless you provided them as functions in a sh script.
    – Kusalananda
    May 25, 2018 at 17:28
  • @Kusalananda Actually, they're POSIX sh things, which bash happens to implement. They should work in a vast majority of standard shells (with the possible exception of CSH style shells). May 25, 2018 at 19:45
  • 4
    @AustinHemmelgarn No, they (pushd/popd) are not mentioned in POSIX at all.
    – Kusalananda
    May 25, 2018 at 20:10

2 Answers 2

3

It is not always possible or useful to run parts of a script in a subshell.

I do use pushd/popd in scripts, too, (doesn't matter because I usually have bashisms in my scripts anyway) but in my understanding this is mainly a convenience feature for an interactive shell, and using subshells there should not be expected to be fun.

2

pushd/popd are easier to read but they are not safe because if script is interrupted (normally or forcefully) in between, you will endup with an altered CWD.

When using subshell there is a guarantee that at the end, you will have the original CWD, regardless how the execution happens.

In my early years of bash, I used pushd/popd but now I avoid them whenever is possible. I still use them on the command line, but not scripts.

When writing script, always think avout the worst case: what could happen if execution breaks on current line.

3
  • 3
    A script that changes its working directory and is interrupted would not change the working directory of the shell that invoked it.
    – Kusalananda
    Jan 4, 2019 at 9:21
  • @Kusalananda, true, but it would effect any commands that happen within the script subsequent to the interrupt (ie: if the script has a trap to cleanup)
    – Lucas
    Nov 15, 2023 at 14:52
  • @Lucas Yes. The nature of a trap handler is that it may be invoked at any time between being installed and being uninstalled, and the programmer needs to keep this in mind when writing it. It is, so to speak, expected that the trap handler may be invoked at any time during its lifetime. This has little to do with my point, though, which was that the act of interrupting a script will not change the working directory for the calling shell.
    – Kusalananda
    Nov 15, 2023 at 20:49

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .