chdir#

Change the process’s current working directory, and update $ENV{PWD} to match.

Synopsis#

use Cwd qw(chdir);
chdir($path) or die $!;

What you get back#

1 on success, 0 on failure. $! is set when the call fails so you can distinguish errors.

Examples#

Change directory and keep $ENV{PWD} consistent for child processes:

use Cwd qw(chdir);
chdir('/tmp') or die "chdir: $!";
system('printenv', 'PWD');       # /tmp

Guard against a missing target:

use Cwd qw(chdir);
unless (chdir('/does/not/exist')) {
    warn "cannot enter directory: $!";
}

Switch directories around a block and return:

use Cwd qw(getcwd chdir);
my $saved = getcwd();
chdir('/var/log') or die $!;

## ... work in /var/log ...

chdir($saved) or die $!;

Edge cases#

  • Called with no argument — returns 0 (unlike the core chdir builtin, which chdirs to $ENV{HOME}). Pass the target explicitly.

  • Target exists but is not a directory — returns 0 with $! set to ENOTDIR.

  • $ENV{PWD} is updated only on success, through the %ENV tied hash, so setenv(3) is called as well.

Differences from upstream#

  • Upstream’s Cwd::chdir normalises slashes in the argument before calling the builtin. pperl passes the path through unchanged and relies on the kernel to handle duplicate separators, which it does.

  • No-argument form returns 0; upstream treats it as chdir('') which is equivalent to chdir to HOME. Scripts that depend on the implicit-HOME form should pass $ENV{HOME} explicitly.

See also#

  • getcwd — absolute path of the current directory

  • abs_path — canonicalise a path without changing directory