How to `touch` and `cat` file named `-` [duplicate]
Clash Royale CLAN TAG#URR8PPP
up vote
4
down vote
favorite
This question already has an answer here:
How do I delete a file whose name begins with â-â (hyphen a.k.a. dash or minus)?
10 answers
How do I use GNU touch
to update a file called -
?
How do I use GNU cat
to display a file called -
?
I'm running:
% cat --version | head -n1
cat (GNU coreutils) 8.29
% touch --version | head -n1
touch (GNU coreutils) 8.29
Firstly, touch
:
% touch -
% ls -l
total 0
% touch -- -
% ls -l -- -
ls: cannot access '-': No such file or directory
Ok, I'll give up on creating a file with touch
. Let's create it with date
instead:
% date > -
% ls -l -
-rw-r--r-- 1 ravi ravi 29 Sep 8 19:54 -
%
Now, let's try to cat
it:
% cat -
% # I pressed ^D
% cat -- -
% # Same again - I pressed ^D
I know I can work around with:
% > -
and
% cat < -
But why don't these GNU utils support the convention that --
means that everything following is treated as a non-option?
How do I use these tools in the general case, for example I have a variable with the contents -
?
linux cat touch
marked as duplicate by Barmar, Jeff Schaller, ñÃÂsýù÷, Thomas, thrig Sep 8 at 14:47
This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.
 |Â
show 3 more comments
up vote
4
down vote
favorite
This question already has an answer here:
How do I delete a file whose name begins with â-â (hyphen a.k.a. dash or minus)?
10 answers
How do I use GNU touch
to update a file called -
?
How do I use GNU cat
to display a file called -
?
I'm running:
% cat --version | head -n1
cat (GNU coreutils) 8.29
% touch --version | head -n1
touch (GNU coreutils) 8.29
Firstly, touch
:
% touch -
% ls -l
total 0
% touch -- -
% ls -l -- -
ls: cannot access '-': No such file or directory
Ok, I'll give up on creating a file with touch
. Let's create it with date
instead:
% date > -
% ls -l -
-rw-r--r-- 1 ravi ravi 29 Sep 8 19:54 -
%
Now, let's try to cat
it:
% cat -
% # I pressed ^D
% cat -- -
% # Same again - I pressed ^D
I know I can work around with:
% > -
and
% cat < -
But why don't these GNU utils support the convention that --
means that everything following is treated as a non-option?
How do I use these tools in the general case, for example I have a variable with the contents -
?
linux cat touch
marked as duplicate by Barmar, Jeff Schaller, ñÃÂsýù÷, Thomas, thrig Sep 8 at 14:47
This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.
@Barmar This is a more specific case where the filename is-
. A lone-
is not an option, so the issue is different from the issues in the questions that you have proposed as duplicates.
â Kusalananda
Sep 8 at 14:04
@Kusalananda A lone-
is going to be treated as an invalid option or a placeholder forstdin
orstdout
. In any case, the solution is the same.
â Barmar
Sep 8 at 14:05
@Barmar Ok, but-
is not an invalid option.
â Kusalananda
Sep 8 at 14:10
@Kusalananda If it's not treated as a synonym for stdin/stdout (astouch
andcat
do), and it's not a filename, and it's not an actual option, what else could it be? But this is immaterial, my point is that you use the same solution to deal with any filename beginning with-
, it doesn't matter why it doesn't work normally.
â Barmar
Sep 8 at 14:14
Forget off the top of my head, but ti was covered in this "game" that teaches you escaping stuff, etc. Really like this series they have for learning a higher level of command line use... and I've been using Linux for 20 years... overthewire.org/wargames/bandit/bandit0.html
â ivanivan
Sep 8 at 14:45
 |Â
show 3 more comments
up vote
4
down vote
favorite
up vote
4
down vote
favorite
This question already has an answer here:
How do I delete a file whose name begins with â-â (hyphen a.k.a. dash or minus)?
10 answers
How do I use GNU touch
to update a file called -
?
How do I use GNU cat
to display a file called -
?
I'm running:
% cat --version | head -n1
cat (GNU coreutils) 8.29
% touch --version | head -n1
touch (GNU coreutils) 8.29
Firstly, touch
:
% touch -
% ls -l
total 0
% touch -- -
% ls -l -- -
ls: cannot access '-': No such file or directory
Ok, I'll give up on creating a file with touch
. Let's create it with date
instead:
% date > -
% ls -l -
-rw-r--r-- 1 ravi ravi 29 Sep 8 19:54 -
%
Now, let's try to cat
it:
% cat -
% # I pressed ^D
% cat -- -
% # Same again - I pressed ^D
I know I can work around with:
% > -
and
% cat < -
But why don't these GNU utils support the convention that --
means that everything following is treated as a non-option?
How do I use these tools in the general case, for example I have a variable with the contents -
?
linux cat touch
This question already has an answer here:
How do I delete a file whose name begins with â-â (hyphen a.k.a. dash or minus)?
10 answers
How do I use GNU touch
to update a file called -
?
How do I use GNU cat
to display a file called -
?
I'm running:
% cat --version | head -n1
cat (GNU coreutils) 8.29
% touch --version | head -n1
touch (GNU coreutils) 8.29
Firstly, touch
:
% touch -
% ls -l
total 0
% touch -- -
% ls -l -- -
ls: cannot access '-': No such file or directory
Ok, I'll give up on creating a file with touch
. Let's create it with date
instead:
% date > -
% ls -l -
-rw-r--r-- 1 ravi ravi 29 Sep 8 19:54 -
%
Now, let's try to cat
it:
% cat -
% # I pressed ^D
% cat -- -
% # Same again - I pressed ^D
I know I can work around with:
% > -
and
% cat < -
But why don't these GNU utils support the convention that --
means that everything following is treated as a non-option?
How do I use these tools in the general case, for example I have a variable with the contents -
?
This question already has an answer here:
How do I delete a file whose name begins with â-â (hyphen a.k.a. dash or minus)?
10 answers
linux cat touch
linux cat touch
edited Sep 8 at 13:32
asked Sep 8 at 13:17
Tom Hale
5,94622776
5,94622776
marked as duplicate by Barmar, Jeff Schaller, ñÃÂsýù÷, Thomas, thrig Sep 8 at 14:47
This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.
marked as duplicate by Barmar, Jeff Schaller, ñÃÂsýù÷, Thomas, thrig Sep 8 at 14:47
This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.
@Barmar This is a more specific case where the filename is-
. A lone-
is not an option, so the issue is different from the issues in the questions that you have proposed as duplicates.
â Kusalananda
Sep 8 at 14:04
@Kusalananda A lone-
is going to be treated as an invalid option or a placeholder forstdin
orstdout
. In any case, the solution is the same.
â Barmar
Sep 8 at 14:05
@Barmar Ok, but-
is not an invalid option.
â Kusalananda
Sep 8 at 14:10
@Kusalananda If it's not treated as a synonym for stdin/stdout (astouch
andcat
do), and it's not a filename, and it's not an actual option, what else could it be? But this is immaterial, my point is that you use the same solution to deal with any filename beginning with-
, it doesn't matter why it doesn't work normally.
â Barmar
Sep 8 at 14:14
Forget off the top of my head, but ti was covered in this "game" that teaches you escaping stuff, etc. Really like this series they have for learning a higher level of command line use... and I've been using Linux for 20 years... overthewire.org/wargames/bandit/bandit0.html
â ivanivan
Sep 8 at 14:45
 |Â
show 3 more comments
@Barmar This is a more specific case where the filename is-
. A lone-
is not an option, so the issue is different from the issues in the questions that you have proposed as duplicates.
â Kusalananda
Sep 8 at 14:04
@Kusalananda A lone-
is going to be treated as an invalid option or a placeholder forstdin
orstdout
. In any case, the solution is the same.
â Barmar
Sep 8 at 14:05
@Barmar Ok, but-
is not an invalid option.
â Kusalananda
Sep 8 at 14:10
@Kusalananda If it's not treated as a synonym for stdin/stdout (astouch
andcat
do), and it's not a filename, and it's not an actual option, what else could it be? But this is immaterial, my point is that you use the same solution to deal with any filename beginning with-
, it doesn't matter why it doesn't work normally.
â Barmar
Sep 8 at 14:14
Forget off the top of my head, but ti was covered in this "game" that teaches you escaping stuff, etc. Really like this series they have for learning a higher level of command line use... and I've been using Linux for 20 years... overthewire.org/wargames/bandit/bandit0.html
â ivanivan
Sep 8 at 14:45
@Barmar This is a more specific case where the filename is
-
. A lone -
is not an option, so the issue is different from the issues in the questions that you have proposed as duplicates.â Kusalananda
Sep 8 at 14:04
@Barmar This is a more specific case where the filename is
-
. A lone -
is not an option, so the issue is different from the issues in the questions that you have proposed as duplicates.â Kusalananda
Sep 8 at 14:04
@Kusalananda A lone
-
is going to be treated as an invalid option or a placeholder for stdin
or stdout
. In any case, the solution is the same.â Barmar
Sep 8 at 14:05
@Kusalananda A lone
-
is going to be treated as an invalid option or a placeholder for stdin
or stdout
. In any case, the solution is the same.â Barmar
Sep 8 at 14:05
@Barmar Ok, but
-
is not an invalid option.â Kusalananda
Sep 8 at 14:10
@Barmar Ok, but
-
is not an invalid option.â Kusalananda
Sep 8 at 14:10
@Kusalananda If it's not treated as a synonym for stdin/stdout (as
touch
and cat
do), and it's not a filename, and it's not an actual option, what else could it be? But this is immaterial, my point is that you use the same solution to deal with any filename beginning with -
, it doesn't matter why it doesn't work normally.â Barmar
Sep 8 at 14:14
@Kusalananda If it's not treated as a synonym for stdin/stdout (as
touch
and cat
do), and it's not a filename, and it's not an actual option, what else could it be? But this is immaterial, my point is that you use the same solution to deal with any filename beginning with -
, it doesn't matter why it doesn't work normally.â Barmar
Sep 8 at 14:14
Forget off the top of my head, but ti was covered in this "game" that teaches you escaping stuff, etc. Really like this series they have for learning a higher level of command line use... and I've been using Linux for 20 years... overthewire.org/wargames/bandit/bandit0.html
â ivanivan
Sep 8 at 14:45
Forget off the top of my head, but ti was covered in this "game" that teaches you escaping stuff, etc. Really like this series they have for learning a higher level of command line use... and I've been using Linux for 20 years... overthewire.org/wargames/bandit/bandit0.html
â ivanivan
Sep 8 at 14:45
 |Â
show 3 more comments
1 Answer
1
active
oldest
votes
up vote
10
down vote
accepted
Use an explicit path to the file:
touch ./-
cat ./-
GNU touch
treats a file operand of -
specially:
A FILE argument string of
-
is handled specially and causestouch
to
change the times of the file associated with standard output.
For cat
, the POSIX standard specifies that a file operand -
should be interpreted as a request to read from standard input.
The double-dash convention is still in effect, but it's not for signalling the end of arguments but the end of options. In neither of these cases would -
be taken as an option (a lone -
can not be an option) but as an operand ("file name argument").
Regarding your last question:
To protect the contents of a variable against being interpreted as a set of options when using it as
utility "$variable"
use
utility -- "$variable"
Note that if the utility is cat
, sed
, awk
, paste
, sort
and possibly a few others (or GNU touch
), and $variable
is -
, this will still cause the utility to do its special processing since, as said above, -
is not an option. Instead, make provisions so that filenames, if they may start with or are equal to -
, are preceded by a path, for example ./
for files in the current working directory.
A good habit is to use
for filename in ./*; do
rather than
for filename in *; do
for example.
It seems the way for absolute belts and braces would be to docat "$(readlink -f "$file")"
â Tom Hale
Sep 8 at 13:35
What about thetouch
case though?
â Tom Hale
Sep 8 at 13:36
@TomHale no.readlink -f
is not portable. What about thetouch
case?
â Kusalananda
Sep 8 at 13:38
So[ "$file" = - ] && file=./-
is needed before each invocation of GNUcat
andtouch
for the truly paranoid? Any nicer ways?
â Tom Hale
Sep 8 at 13:40
4
@TomHale If you're looping over files in a directory, make a habit of usingfor file in ./*
or similar, instead offor file in *
.
â Kusalananda
Sep 8 at 13:43
 |Â
show 1 more comment
1 Answer
1
active
oldest
votes
1 Answer
1
active
oldest
votes
active
oldest
votes
active
oldest
votes
up vote
10
down vote
accepted
Use an explicit path to the file:
touch ./-
cat ./-
GNU touch
treats a file operand of -
specially:
A FILE argument string of
-
is handled specially and causestouch
to
change the times of the file associated with standard output.
For cat
, the POSIX standard specifies that a file operand -
should be interpreted as a request to read from standard input.
The double-dash convention is still in effect, but it's not for signalling the end of arguments but the end of options. In neither of these cases would -
be taken as an option (a lone -
can not be an option) but as an operand ("file name argument").
Regarding your last question:
To protect the contents of a variable against being interpreted as a set of options when using it as
utility "$variable"
use
utility -- "$variable"
Note that if the utility is cat
, sed
, awk
, paste
, sort
and possibly a few others (or GNU touch
), and $variable
is -
, this will still cause the utility to do its special processing since, as said above, -
is not an option. Instead, make provisions so that filenames, if they may start with or are equal to -
, are preceded by a path, for example ./
for files in the current working directory.
A good habit is to use
for filename in ./*; do
rather than
for filename in *; do
for example.
It seems the way for absolute belts and braces would be to docat "$(readlink -f "$file")"
â Tom Hale
Sep 8 at 13:35
What about thetouch
case though?
â Tom Hale
Sep 8 at 13:36
@TomHale no.readlink -f
is not portable. What about thetouch
case?
â Kusalananda
Sep 8 at 13:38
So[ "$file" = - ] && file=./-
is needed before each invocation of GNUcat
andtouch
for the truly paranoid? Any nicer ways?
â Tom Hale
Sep 8 at 13:40
4
@TomHale If you're looping over files in a directory, make a habit of usingfor file in ./*
or similar, instead offor file in *
.
â Kusalananda
Sep 8 at 13:43
 |Â
show 1 more comment
up vote
10
down vote
accepted
Use an explicit path to the file:
touch ./-
cat ./-
GNU touch
treats a file operand of -
specially:
A FILE argument string of
-
is handled specially and causestouch
to
change the times of the file associated with standard output.
For cat
, the POSIX standard specifies that a file operand -
should be interpreted as a request to read from standard input.
The double-dash convention is still in effect, but it's not for signalling the end of arguments but the end of options. In neither of these cases would -
be taken as an option (a lone -
can not be an option) but as an operand ("file name argument").
Regarding your last question:
To protect the contents of a variable against being interpreted as a set of options when using it as
utility "$variable"
use
utility -- "$variable"
Note that if the utility is cat
, sed
, awk
, paste
, sort
and possibly a few others (or GNU touch
), and $variable
is -
, this will still cause the utility to do its special processing since, as said above, -
is not an option. Instead, make provisions so that filenames, if they may start with or are equal to -
, are preceded by a path, for example ./
for files in the current working directory.
A good habit is to use
for filename in ./*; do
rather than
for filename in *; do
for example.
It seems the way for absolute belts and braces would be to docat "$(readlink -f "$file")"
â Tom Hale
Sep 8 at 13:35
What about thetouch
case though?
â Tom Hale
Sep 8 at 13:36
@TomHale no.readlink -f
is not portable. What about thetouch
case?
â Kusalananda
Sep 8 at 13:38
So[ "$file" = - ] && file=./-
is needed before each invocation of GNUcat
andtouch
for the truly paranoid? Any nicer ways?
â Tom Hale
Sep 8 at 13:40
4
@TomHale If you're looping over files in a directory, make a habit of usingfor file in ./*
or similar, instead offor file in *
.
â Kusalananda
Sep 8 at 13:43
 |Â
show 1 more comment
up vote
10
down vote
accepted
up vote
10
down vote
accepted
Use an explicit path to the file:
touch ./-
cat ./-
GNU touch
treats a file operand of -
specially:
A FILE argument string of
-
is handled specially and causestouch
to
change the times of the file associated with standard output.
For cat
, the POSIX standard specifies that a file operand -
should be interpreted as a request to read from standard input.
The double-dash convention is still in effect, but it's not for signalling the end of arguments but the end of options. In neither of these cases would -
be taken as an option (a lone -
can not be an option) but as an operand ("file name argument").
Regarding your last question:
To protect the contents of a variable against being interpreted as a set of options when using it as
utility "$variable"
use
utility -- "$variable"
Note that if the utility is cat
, sed
, awk
, paste
, sort
and possibly a few others (or GNU touch
), and $variable
is -
, this will still cause the utility to do its special processing since, as said above, -
is not an option. Instead, make provisions so that filenames, if they may start with or are equal to -
, are preceded by a path, for example ./
for files in the current working directory.
A good habit is to use
for filename in ./*; do
rather than
for filename in *; do
for example.
Use an explicit path to the file:
touch ./-
cat ./-
GNU touch
treats a file operand of -
specially:
A FILE argument string of
-
is handled specially and causestouch
to
change the times of the file associated with standard output.
For cat
, the POSIX standard specifies that a file operand -
should be interpreted as a request to read from standard input.
The double-dash convention is still in effect, but it's not for signalling the end of arguments but the end of options. In neither of these cases would -
be taken as an option (a lone -
can not be an option) but as an operand ("file name argument").
Regarding your last question:
To protect the contents of a variable against being interpreted as a set of options when using it as
utility "$variable"
use
utility -- "$variable"
Note that if the utility is cat
, sed
, awk
, paste
, sort
and possibly a few others (or GNU touch
), and $variable
is -
, this will still cause the utility to do its special processing since, as said above, -
is not an option. Instead, make provisions so that filenames, if they may start with or are equal to -
, are preceded by a path, for example ./
for files in the current working directory.
A good habit is to use
for filename in ./*; do
rather than
for filename in *; do
for example.
edited Sep 8 at 15:20
answered Sep 8 at 13:24
Kusalananda
107k14209331
107k14209331
It seems the way for absolute belts and braces would be to docat "$(readlink -f "$file")"
â Tom Hale
Sep 8 at 13:35
What about thetouch
case though?
â Tom Hale
Sep 8 at 13:36
@TomHale no.readlink -f
is not portable. What about thetouch
case?
â Kusalananda
Sep 8 at 13:38
So[ "$file" = - ] && file=./-
is needed before each invocation of GNUcat
andtouch
for the truly paranoid? Any nicer ways?
â Tom Hale
Sep 8 at 13:40
4
@TomHale If you're looping over files in a directory, make a habit of usingfor file in ./*
or similar, instead offor file in *
.
â Kusalananda
Sep 8 at 13:43
 |Â
show 1 more comment
It seems the way for absolute belts and braces would be to docat "$(readlink -f "$file")"
â Tom Hale
Sep 8 at 13:35
What about thetouch
case though?
â Tom Hale
Sep 8 at 13:36
@TomHale no.readlink -f
is not portable. What about thetouch
case?
â Kusalananda
Sep 8 at 13:38
So[ "$file" = - ] && file=./-
is needed before each invocation of GNUcat
andtouch
for the truly paranoid? Any nicer ways?
â Tom Hale
Sep 8 at 13:40
4
@TomHale If you're looping over files in a directory, make a habit of usingfor file in ./*
or similar, instead offor file in *
.
â Kusalananda
Sep 8 at 13:43
It seems the way for absolute belts and braces would be to do
cat "$(readlink -f "$file")"
â Tom Hale
Sep 8 at 13:35
It seems the way for absolute belts and braces would be to do
cat "$(readlink -f "$file")"
â Tom Hale
Sep 8 at 13:35
What about the
touch
case though?â Tom Hale
Sep 8 at 13:36
What about the
touch
case though?â Tom Hale
Sep 8 at 13:36
@TomHale no.
readlink -f
is not portable. What about the touch
case?â Kusalananda
Sep 8 at 13:38
@TomHale no.
readlink -f
is not portable. What about the touch
case?â Kusalananda
Sep 8 at 13:38
So
[ "$file" = - ] && file=./-
is needed before each invocation of GNU cat
and touch
for the truly paranoid? Any nicer ways?â Tom Hale
Sep 8 at 13:40
So
[ "$file" = - ] && file=./-
is needed before each invocation of GNU cat
and touch
for the truly paranoid? Any nicer ways?â Tom Hale
Sep 8 at 13:40
4
4
@TomHale If you're looping over files in a directory, make a habit of using
for file in ./*
or similar, instead of for file in *
.â Kusalananda
Sep 8 at 13:43
@TomHale If you're looping over files in a directory, make a habit of using
for file in ./*
or similar, instead of for file in *
.â Kusalananda
Sep 8 at 13:43
 |Â
show 1 more comment
@Barmar This is a more specific case where the filename is
-
. A lone-
is not an option, so the issue is different from the issues in the questions that you have proposed as duplicates.â Kusalananda
Sep 8 at 14:04
@Kusalananda A lone
-
is going to be treated as an invalid option or a placeholder forstdin
orstdout
. In any case, the solution is the same.â Barmar
Sep 8 at 14:05
@Barmar Ok, but
-
is not an invalid option.â Kusalananda
Sep 8 at 14:10
@Kusalananda If it's not treated as a synonym for stdin/stdout (as
touch
andcat
do), and it's not a filename, and it's not an actual option, what else could it be? But this is immaterial, my point is that you use the same solution to deal with any filename beginning with-
, it doesn't matter why it doesn't work normally.â Barmar
Sep 8 at 14:14
Forget off the top of my head, but ti was covered in this "game" that teaches you escaping stuff, etc. Really like this series they have for learning a higher level of command line use... and I've been using Linux for 20 years... overthewire.org/wargames/bandit/bandit0.html
â ivanivan
Sep 8 at 14:45