|
|
1.1 root 1:
2: /* /sccs/src/cmd/uucp/s.cpmv.c
3: cpmv.c 1.4 8/30/84 17:37:15
4: */
5: #include "uucp.h"
6: VERSION(@(#) c cpmv.c 1.4);
7:
8: /*
9: * copy f1 to f2 locally
10: * f1 -> source file name
11: * f2 -> destination file name
12: * return:
13: * 0 -> ok
14: * FAIL -> failed
15: */
16:
17: xcp(f1, f2)
18: char *f1, *f2;
19: {
20: register FILE *fp1, *fp2;
21: register int n;
22: char buf[BUFSIZ];
23: char full[MAXFULLNAME];
24:
25: if ((fp1 = fopen(f1, "r")) == NULL)
26: return(FAIL);
27: (void) strcpy(full, f2);
28: if (DIRECTORY(f2)) {
29: (void) strcat(full, "/");
30: (void) strcat(full, BASENAME(f1, '/'));
31: (void) strcpy(f2, full);
32: }
33:
34: DEBUG(4, "full %s\n", full);
35: if ((fp2 = fopen(full, "w")) == NULL) {
36: (void) fclose(fp1);
37: return(FAIL);
38: }
39: (void) chmod(full, 0666);
40:
41: /* copy -- check errors later */
42: while ( (n = fread(buf, sizeof (char), sizeof buf, fp1)) != 0)
43: (void) fwrite(buf, sizeof (char), n, fp2);
44:
45: /* check for any errors */
46: n = ferror(fp1) | ferror(fp2);
47: n |= fclose(fp1) | fclose(fp2);
48:
49: if (n)
50: return(FAIL);
51: return(0);
52: }
53:
54:
55: /*
56: * move f1 to f2 locally
57: * returns:
58: * 0 -> ok
59: * FAIL -> failed
60: */
61:
62: xmv(f1, f2)
63: register char *f1, *f2;
64: {
65: register int ret;
66: int oerrno = 0;
67:
68: (void) unlink(f2); /* i'm convinced this is the right thing to do */
69: if ( (ret = link(f1, f2)) < 0) {
70: oerrno = errno;
71: /* copy file */
72: ret = xcp(f1, f2);
73: }
74:
75: if (ret == 0)
76: (void) unlink(f1);
77: /*
78: * ugh
79: */
80: if (ret < 0) {
81: char buf[BUFSIZ];
82: char f2base[BUFSIZ];
83: struct stat s1, s2;
84: char *p;
85: char *strrchr();
86:
87: s1.st_mode = 0;
88: s2.st_mode = 0;
89: if (stat(f1, &s1) < 0)
90: s1.st_mode = -1;
91: strcpy(f2base, f2);
92: if ((p = strrchr(f2base, '/')) != 0)
93: *p = 0;
94: if (stat(f2base, &s2) < 0)
95: s2.st_mode = -1;
96: sprintf(buf, "bad xmv: %s (%o) -> %s (%o); ln errno %d",
97: f1, s1.st_mode, f2base, s2.st_mode, oerrno);
98: logent(buf, "DEBUG");
99: }
100: return(ret);
101: }
102:
103:
104: /* toCorrupt - move file to CORRUPTDIR
105: * return - none
106: */
107:
108: void
109: toCorrupt(file)
110: char *file;
111: {
112: char corrupt[MAXFULLNAME];
113:
114: (void) sprintf(corrupt, "%s/%s", CORRUPTDIR, BASENAME(file, '/'));
115: (void) link(file, corrupt);
116: ASSERT(unlink(file) == 0, Ct_UNLINK, file, errno);
117: return;
118: }
119:
120: /*
121: * append f1 to f2
122: * f1 -> source FILE pointer
123: * f2 -> destination FILE pointer
124: * return:
125: * SUCCESS -> ok
126: * FAIL -> failed
127: */
128: xfappend(fp1, fp2)
129: register FILE *fp1, *fp2;
130: {
131: register int nc;
132: char buf[BUFSIZ];
133:
134: while ((nc = fread(buf, sizeof (char), BUFSIZ, fp1)) > 0)
135: (void) fwrite(buf, sizeof (char), nc, fp2);
136:
137: return(ferror(fp1) || ferror(fp2) ? FAIL : SUCCESS);
138: }
139:
140:
141: /*
142: * copy f1 to f2 locally under uid of uid argument
143: * f1 -> source file name
144: * f2 -> destination file name
145: * Uid and Euid are global
146: * return:
147: * 0 -> ok
148: * FAIL -> failed
149: * NOTES:
150: * for V7 systems, flip-flop between real and effective uid is
151: * not allowed, so fork must be done. This code will not
152: * work correctly when realuid is root on System 5 because of
153: * a bug in setuid.
154: */
155:
156: #ifndef uidxcp
157:
158: uidxcp(f1, f2)
159: char *f1, *f2;
160: {
161: int status;
162: char full[MAXFULLNAME];
163: register pid, rpid;
164:
165: (void) strcpy(full, f2);
166: if (DIRECTORY(f2)) {
167: (void) strcat(full, "/");
168: (void) strcat(full, BASENAME(f1, '/'));
169: }
170:
171: /* create full owned by uucp */
172: (void) close(creat(full, 0666));
173: (void) chmod(full, 0666);
174:
175: /* do file copy as read uid */
176: #ifndef V7
177: (void) setuid(Uid);
178: status = xcp(f1, full);
179: (void) setuid(Euid);
180: return(status);
181:
182: #else
183:
184: if ((pid = vfork()) == 0) {
185: setuid(Uid);
186: _exit (xcp(f1, full));
187: }
188: status = 1;
189: while ((rpid = wait(&status)) != pid && rpid != -1)
190: ;
191: return (rpid == -1 ? 1 : status);
192: #endif
193: }
194:
195: #endif
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.