Implement the -C (-o noclobber) option, which prevents existing regular
files from being overwritten by shell redirection.
This commit is contained in:
parent
ce1c850d62
commit
1a958c6653
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=96922
@ -247,6 +247,7 @@ STATIC const struct errname errormsg[] = {
|
||||
#ifdef ELIBACC
|
||||
{ ELIBACC, E_EXEC, "shared library missing" },
|
||||
#endif
|
||||
{ EEXIST, E_CREAT, "file exists" },
|
||||
{ 0, 0, NULL },
|
||||
};
|
||||
|
||||
|
@ -448,6 +448,7 @@ expredir(union node *n)
|
||||
case NTO:
|
||||
case NFROMTO:
|
||||
case NAPPEND:
|
||||
case NCLOBBER:
|
||||
expandarg(redir->nfile.fname, &fn, EXP_TILDE | EXP_REDIR);
|
||||
redir->nfile.expfname = fn.list->text;
|
||||
break;
|
||||
|
@ -1057,6 +1057,8 @@ cmdtxt(union node *n)
|
||||
p = ">>"; i = 1; goto redir;
|
||||
case NTOFD:
|
||||
p = ">&"; i = 1; goto redir;
|
||||
case NCLOBBER:
|
||||
p = ">|"; i = 1; goto redir;
|
||||
case NFROM:
|
||||
p = "<"; i = 0; goto redir;
|
||||
case NFROMTO:
|
||||
|
@ -120,6 +120,7 @@ NTO nfile # fd> fname
|
||||
NFROM nfile # fd< fname
|
||||
NFROMTO nfile # fd<> fname
|
||||
NAPPEND nfile # fd>> fname
|
||||
NCLOBBER nfile # fd>| fname
|
||||
type int
|
||||
next nodeptr # next redirection in list
|
||||
fd int # file descriptor being redirected
|
||||
|
@ -1145,6 +1145,8 @@ parseredir: {
|
||||
np->type = NAPPEND;
|
||||
else if (c == '&')
|
||||
np->type = NTOFD;
|
||||
else if (c == '|')
|
||||
np->type = NCLOBBER;
|
||||
else {
|
||||
np->type = NTO;
|
||||
pungetc();
|
||||
|
@ -43,6 +43,7 @@ static const char rcsid[] =
|
||||
#endif /* not lint */
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <signal.h>
|
||||
#include <string.h>
|
||||
#include <fcntl.h>
|
||||
@ -62,6 +63,7 @@ static const char rcsid[] =
|
||||
#include "output.h"
|
||||
#include "memalloc.h"
|
||||
#include "error.h"
|
||||
#include "options.h"
|
||||
|
||||
|
||||
#define EMPTY -2 /* marks an unused slot in redirtab */
|
||||
@ -161,6 +163,7 @@ redirect(union node *redir, int flags)
|
||||
STATIC void
|
||||
openredirect(union node *redir, char memory[10])
|
||||
{
|
||||
struct stat sb;
|
||||
int fd = redir->nfile.fd;
|
||||
char *fname;
|
||||
int f;
|
||||
@ -207,6 +210,9 @@ openredirect(union node *redir, char memory[10])
|
||||
goto movefd;
|
||||
case NTO:
|
||||
fname = redir->nfile.expfname;
|
||||
if (Cflag && stat(fname, &sb) != -1 && S_ISREG(sb.st_mode))
|
||||
error("cannot create %s: %s", fname,
|
||||
errmsg(EEXIST, E_CREAT));
|
||||
#ifdef O_CREAT
|
||||
if ((f = open(fname, O_WRONLY|O_CREAT|O_TRUNC, 0666)) < 0)
|
||||
error("cannot create %s: %s", fname, errmsg(errno, E_CREAT));
|
||||
@ -215,6 +221,11 @@ openredirect(union node *redir, char memory[10])
|
||||
error("cannot create %s: %s", fname, errmsg(errno, E_CREAT));
|
||||
#endif
|
||||
goto movefd;
|
||||
case NCLOBBER:
|
||||
fname = redir->nfile.expfname;
|
||||
if ((f = open(fname, O_WRONLY|O_CREAT|O_TRUNC, 0666)) < 0)
|
||||
error("cannot create %s: %s", fname, errmsg(errno, E_CREAT));
|
||||
goto movefd;
|
||||
case NAPPEND:
|
||||
fname = redir->nfile.expfname;
|
||||
#ifdef O_APPEND
|
||||
|
@ -195,7 +195,6 @@ completion.
|
||||
.It Fl C Li noclobber
|
||||
Do not overwrite existing files with
|
||||
.Dq Li > .
|
||||
(UNIMPLEMENTED)
|
||||
.It Fl E Li emacs
|
||||
Enable the builtin
|
||||
.Xr emacs 1
|
||||
|
@ -142,6 +142,7 @@ shcmd(union node *cmd, FILE *fp)
|
||||
case NTO: s = ">"; dftfd = 1; break;
|
||||
case NAPPEND: s = ">>"; dftfd = 1; break;
|
||||
case NTOFD: s = ">&"; dftfd = 1; break;
|
||||
case NCLOBBER: s = ">|"; dftfd = 1; break;
|
||||
case NFROM: s = "<"; dftfd = 0; break;
|
||||
case NFROMTO: s = "<>"; dftfd = 0; break;
|
||||
case NFROMFD: s = "<&"; dftfd = 0; break;
|
||||
|
Loading…
Reference in New Issue
Block a user