updated signal names; allow kill -0
[unix-history] / usr / src / bin / rm / rm.c
CommitLineData
6b7bfa6e 1static char *sccsid = "@(#)rm.c 4.12 (Berkeley) %G%";
ae80f4a2
BJ
2int errcode;
3
4#include <stdio.h>
d7ab2ea5 5#include <sys/param.h>
ae80f4a2 6#include <sys/stat.h>
6b7bfa6e 7#include <sys/dir.h>
ae80f4a2
BJ
8
9char *sprintf();
10
11main(argc, argv)
12char *argv[];
13{
14 register char *arg;
15 int fflg, iflg, rflg;
16
17 fflg = 0;
18 if (isatty(0) == 0)
19 fflg++;
20 iflg = 0;
21 rflg = 0;
22 while(argc>1 && argv[1][0]=='-') {
23 arg = *++argv;
24 argc--;
ca02483b
BJ
25
26 /*
27 * all files following a null option are considered file names
28 */
29 if (*(arg+1) == '\0') break;
30
ae80f4a2
BJ
31 while(*++arg != '\0')
32 switch(*arg) {
33 case 'f':
34 fflg++;
35 break;
36 case 'i':
37 iflg++;
38 break;
39 case 'r':
40 rflg++;
41 break;
42 default:
43 printf("rm: unknown option %s\n", *argv);
44 exit(1);
45 }
46 }
47 while(--argc > 0) {
48 if(!strcmp(*++argv, "..")) {
49 fprintf(stderr, "rm: cannot remove `..'\n");
50 continue;
51 }
52 rm(*argv, fflg, rflg, iflg, 0);
53 }
54
55 exit(errcode);
56}
57
58rm(arg, fflg, rflg, iflg, level)
59char arg[];
60{
61 struct stat buf;
c1a06f06
KM
62 struct direct *dp;
63 DIR *dirp;
64 char name[BUFSIZ];
ae80f4a2
BJ
65 int d;
66
dd3897d5 67 if(lstat(arg, &buf)) {
ae80f4a2
BJ
68 if (fflg==0) {
69 printf("rm: %s nonexistent\n", arg);
70 ++errcode;
71 }
72 return;
73 }
74 if ((buf.st_mode&S_IFMT) == S_IFDIR) {
75 if(rflg) {
76 if (access(arg, 02) < 0) {
77 if (fflg==0)
78 printf("%s not changed\n", arg);
79 errcode++;
80 return;
81 }
82 if(iflg && level!=0) {
28c2b1a2 83 printf("remove directory %s? ", arg);
ae80f4a2
BJ
84 if(!yes())
85 return;
86 }
c1a06f06 87 if((dirp = opendir(arg)) == NULL) {
28c2b1a2 88 printf("rm: cannot read %s?\n", arg);
ae80f4a2
BJ
89 exit(1);
90 }
c1a06f06
KM
91 while((dp = readdir(dirp)) != NULL) {
92 if(dp->d_ino != 0 && !dotname(dp->d_name)) {
dfbe9024 93 sprintf(name, "%s/%s", arg, dp->d_name);
ae80f4a2
BJ
94 rm(name, fflg, rflg, iflg, level+1);
95 }
96 }
c1a06f06 97 closedir(dirp);
fc96c1d6
SL
98 if (dotname(arg))
99 return;
100 if (iflg) {
101 printf("rm: remove %s? ", arg);
102 if (!yes())
103 return;
104 }
105 if (rmdir(arg) < 0) {
6b7bfa6e 106 fprintf(stderr, "rm: ");
fc96c1d6
SL
107 perror(arg);
108 errcode++;
109 }
ae80f4a2
BJ
110 return;
111 }
112 printf("rm: %s directory\n", arg);
113 ++errcode;
114 return;
115 }
116
117 if(iflg) {
28c2b1a2 118 printf("rm: remove %s? ", arg);
ae80f4a2
BJ
119 if(!yes())
120 return;
121 }
122 else if(!fflg) {
0ceff6e6 123 if ((buf.st_mode&S_IFMT) != S_IFLNK && access(arg, 02) < 0) {
dfbe9024
BJ
124 printf("rm: override protection %o for %s? ", buf.st_mode&0777, arg);
125 if(!yes())
ae80f4a2
BJ
126 return;
127 }
128 }
129 if(unlink(arg) && (fflg==0 || iflg)) {
130 printf("rm: %s not removed\n", arg);
131 ++errcode;
132 }
133}
134
135dotname(s)
136char *s;
137{
138 if(s[0] == '.')
139 if(s[1] == '.')
140 if(s[2] == '\0')
141 return(1);
142 else
143 return(0);
144 else if(s[1] == '\0')
145 return(1);
146 return(0);
147}
148
ae80f4a2
BJ
149yes()
150{
151 int i, b;
152
153 i = b = getchar();
154 while(b != '\n' && b != EOF)
155 b = getchar();
156 return(i == 'y');
157}