2

I'm trying to copy the current directory as a source. Using full paths gives me the expected behaviour, copying the entire directory into the destination.

$ cd /tmp
$ mkdir a b
$ cd a
$ touch 1 2 3
$ cp -r /tmp/a /tmp/b # use /tmp/a as source
$ ls /tmp/b
a

However, using . to refer to the source copies the contents of the source instead of the directory itself.

$ cd /tmp
$ mkdir c
$ cd a
$ cp -r . /tmp/c # use . as source
$ ls /tmp/c
1 2 3

What is the difference between . and the absolute path of the current directory? If I want to copy the current directory itself, is there a short reference? (The only way I could see was to use ../a, which seems slightly redundant.)

2
  • . is also used to execute a script. It will also specify the current directory for citing a command or script to run from the current directory vs. the $PATH. e.g. ". ./ping" to run your own custom ping script.
    – MikeP
    Commented Nov 1, 2016 at 0:32
  • 1
    @MikeP Right, but in this case specifying the full path or . would still have the same result. e.g. /path/to/custom/ping vs. ./ping.
    – Sparhawk
    Commented Nov 1, 2016 at 0:37

2 Answers 2

3

In the first case you're asking cp to copy /tmp/a and its contents to /tmp/b; so first a is copied, to /tmp/b/a, then a's contents are copied into /tmp/b/a.

In the second case you're asking cp to copy . and its contents to /tmp/b; using the same thought process as above, we can think of this as copying . first, to /tmp/b/. (i.e. /tmp/b), then copying .'s contents into /tmp/b/..

There is no short reference for the current directory which can work in all cases, since the current directory may have different names (using symlinks). I think the closest you can get is $PWD.

3
  • Ahhh… so if I understand correctly, it's not like there is variable expansion of . in the first place (as would occur if I used $PWD)? The shell copies a pseudo-filename ., which has a different meaning depending on its parent directory.
    – Sparhawk
    Commented Jan 15, 2016 at 22:55
  • 2
    Yes, the shell doesn't process . at all; that's just passed to cp. The shell itself isn't involved in copying. . is just a special directory which exists everywhere and points to itself (look at the inode numbers you get when you run cd /tmp/a; ls -ail; ls -aild ../a, you'll see the inode for . when you're in /tmp/a is the same as /tmp/a's). Commented Jan 15, 2016 at 23:01
  • . and .. are aliases added on filesystem interpretation level in OS. . is always pointing to the current directory. .. is always pointing to it's parent, or in case of /, to itself. These are shell independent. So why have $PWD? Because it returns the whole path as text. . is always relative.
    – Ctrl-C
    Commented May 11, 2018 at 12:46
3

Using . has certain advantages. E.g. you can copy a directory without having to care whether it already exists as target (the parent directory does have to exist, though):

Depending on whether /tmp/target is an existing directory the command

cp -a /path/to/source/dir /tmp/target

leads to different results. But

cp -a /path/to/source/dir/. /tmp/target

has the same result in both cases.

You must log in to answer this question.

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