make '' default to file beginning if no large movements yet
[unix-history] / usr / src / usr.bin / rdist / main.c
CommitLineData
7172eb74
DF
1/*
2 * Copyright (c) 1983 Regents of the University of California.
0718fb71
KB
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms are permitted
b36fc510
KB
6 * provided that the above copyright notice and this paragraph are
7 * duplicated in all such forms and that any documentation,
8 * advertising materials, and other materials related to such
9 * distribution and use acknowledge that the software was developed
10 * by the University of California, Berkeley. The name of the
11 * University may not be used to endorse or promote products derived
12 * from this software without specific prior written permission.
13 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
14 * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
15 * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
7172eb74
DF
16 */
17
18#ifndef lint
19char copyright[] =
20"@(#) Copyright (c) 1983 Regents of the University of California.\n\
21 All rights reserved.\n";
0718fb71 22#endif /* not lint */
7172eb74 23
29e83471 24#ifndef lint
b36fc510 25static char sccsid[] = "@(#)main.c 5.3 (Berkeley) %G%";
0718fb71 26#endif /* not lint */
29e83471
RC
27
28#include "defs.h"
29
78a18ca3
RC
30#define NHOSTS 100
31
29e83471
RC
32/*
33 * Remote distribution program.
34 */
35
be5872f6 36char *distfile = NULL;
d6bccb44 37char tmpfile[] = "/tmp/rdistXXXXXX";
82572cb6 38char *tmpname = &tmpfile[5];
29e83471
RC
39
40int debug; /* debugging flag */
41int nflag; /* NOP flag, just print commands without executing */
42int qflag; /* Quiet. Don't print messages */
f7770429 43int options; /* global options */
29e83471
RC
44int iamremote; /* act as remote server for transfering files */
45
29e83471 46FILE *fin = NULL; /* input file pointer */
0fccdfef 47int rem = -1; /* file descriptor to remote source/sink process */
29e83471 48char host[32]; /* host name */
0fccdfef 49int nerrs; /* number of errors while sending/receiving */
29e83471
RC
50char user[10]; /* user's name */
51char homedir[128]; /* user's home directory */
52int userid; /* user's user ID */
82572cb6 53int groupid; /* user's group ID */
29e83471 54
e8109cf8
RC
55struct passwd *pw; /* pointer to static area used by getpwent */
56struct group *gr; /* pointer to static area used by getgrent */
57
29e83471
RC
58main(argc, argv)
59 int argc;
60 char *argv[];
61{
62 register char *arg;
f7770429 63 int cmdargs = 0;
78a18ca3 64 char *dhosts[NHOSTS], **hp = dhosts;
29e83471 65
29e83471 66 pw = getpwuid(userid = getuid());
29e83471 67 if (pw == NULL) {
82572cb6 68 fprintf(stderr, "%s: Who are you?\n", argv[0]);
29e83471
RC
69 exit(1);
70 }
71 strcpy(user, pw->pw_name);
72 strcpy(homedir, pw->pw_dir);
82572cb6 73 groupid = pw->pw_gid;
29e83471
RC
74 gethostname(host, sizeof(host));
75
76 while (--argc > 0) {
77 if ((arg = *++argv)[0] != '-')
78 break;
79 if (!strcmp(arg, "-Server"))
80 iamremote++;
81 else while (*++arg)
82 switch (*arg) {
83 case 'f':
84 if (--argc <= 0)
85 usage();
86 distfile = *++argv;
87 if (distfile[0] == '-' && distfile[1] == '\0')
88 fin = stdin;
89 break;
90
78a18ca3
RC
91 case 'm':
92 if (--argc <= 0)
93 usage();
94 if (hp >= &dhosts[NHOSTS-2]) {
95 fprintf(stderr, "rdist: too many destination hosts\n");
96 exit(1);
97 }
98 *hp++ = *++argv;
99 break;
100
29e83471 101 case 'd':
82572cb6
RC
102 if (--argc <= 0)
103 usage();
104 define(*++argv);
105 break;
106
107 case 'D':
29e83471
RC
108 debug++;
109 break;
110
f7770429
RC
111 case 'c':
112 cmdargs++;
113 break;
114
29e83471 115 case 'n':
d6bccb44
RC
116 if (options & VERIFY) {
117 printf("rdist: -n overrides -v\n");
118 options &= ~VERIFY;
119 }
29e83471
RC
120 nflag++;
121 break;
122
123 case 'q':
124 qflag++;
125 break;
126
024fde5b
RC
127 case 'b':
128 options |= COMPARE;
129 break;
130
d6bccb44 131 case 'R':
d1dee8e8
RC
132 options |= REMOVE;
133 break;
134
29e83471 135 case 'v':
d6bccb44
RC
136 if (nflag) {
137 printf("rdist: -n overrides -v\n");
138 break;
139 }
f7770429
RC
140 options |= VERIFY;
141 break;
142
143 case 'w':
144 options |= WHOLE;
29e83471
RC
145 break;
146
147 case 'y':
f7770429 148 options |= YOUNGER;
29e83471
RC
149 break;
150
a3e6fd64
RC
151 case 'h':
152 options |= FOLLOW;
153 break;
154
155 case 'i':
156 options |= IGNLNKS;
157 break;
158
29e83471
RC
159 default:
160 usage();
161 }
162 }
78a18ca3 163 *hp = NULL;
82572cb6 164
80babee1 165 setreuid(0, userid);
82572cb6 166 mktemp(tmpfile);
0fccdfef 167
29e83471
RC
168 if (iamremote) {
169 server();
80babee1 170 exit(nerrs != 0);
29e83471 171 }
29e83471 172
f7770429
RC
173 if (cmdargs)
174 docmdargs(argc, argv);
175 else {
be5872f6
JB
176 if (fin == NULL) {
177 if(distfile == NULL) {
178 if((fin = fopen("distfile","r")) == NULL)
179 fin = fopen("Distfile", "r");
180 } else
181 fin = fopen(distfile, "r");
182 if(fin == NULL) {
183 perror(distfile ? distfile : "distfile");
184 exit(1);
185 }
f7770429
RC
186 }
187 yyparse();
0fccdfef 188 if (nerrs == 0)
78a18ca3 189 docmds(dhosts, argc, argv);
82572cb6
RC
190 }
191
80babee1 192 exit(nerrs != 0);
29e83471
RC
193}
194
195usage()
196{
78a18ca3 197 printf("Usage: rdist [-nqbhirvwyD] [-f distfile] [-d var=value] [-m host] [file ...]\n");
a3e6fd64 198 printf("or: rdist [-nqbhirvwyD] -c source [...] machine[:dest]\n");
82572cb6
RC
199 exit(1);
200}
201
f7770429
RC
202/*
203 * rcp like interface for distributing files.
204 */
205docmdargs(nargs, args)
206 int nargs;
207 char *args[];
208{
0fccdfef
RC
209 register struct namelist *nl, *prev;
210 register char *cp;
211 struct namelist *files, *hosts;
212 struct subcmd *cmds;
213 char *dest;
214 static struct namelist tnl = { NULL, NULL };
f7770429 215 int i;
f7770429
RC
216
217 if (nargs < 2)
218 usage();
219
220 prev = NULL;
0fccdfef
RC
221 for (i = 0; i < nargs - 1; i++) {
222 nl = makenl(args[i]);
223 if (prev == NULL)
224 files = prev = nl;
225 else {
226 prev->n_next = nl;
227 prev = nl;
228 }
f7770429
RC
229 }
230
0fccdfef
RC
231 cp = args[i];
232 if ((dest = index(cp, ':')) != NULL)
233 *dest++ = '\0';
234 tnl.n_name = cp;
235 hosts = expand(&tnl, E_ALL);
78a18ca3
RC
236 if (nerrs)
237 exit(1);
f7770429 238
0fccdfef 239 if (dest == NULL || *dest == '\0')
f7770429
RC
240 cmds = NULL;
241 else {
0fccdfef
RC
242 cmds = makesubcmd(INSTALL);
243 cmds->sc_options = options;
244 cmds->sc_name = dest;
f7770429
RC
245 }
246
247 if (debug) {
248 printf("docmdargs()\nfiles = ");
249 prnames(files);
250 printf("hosts = ");
251 prnames(hosts);
252 }
032b4373 253 insert(NULL, files, hosts, cmds);
78a18ca3 254 docmds(NULL, 0, NULL);
29e83471
RC
255}
256
257/*
258 * Print a list of NAME blocks (mostly for debugging).
259 */
0fccdfef
RC
260prnames(nl)
261 register struct namelist *nl;
29e83471
RC
262{
263 printf("( ");
0fccdfef
RC
264 while (nl != NULL) {
265 printf("%s ", nl->n_name);
266 nl = nl->n_next;
29e83471
RC
267 }
268 printf(")\n");
269}
270
271/*VARARGS*/
272warn(fmt, a1, a2,a3)
273 char *fmt;
274{
275 extern int yylineno;
276
277 fprintf(stderr, "rdist: line %d: Warning: ", yylineno);
278 fprintf(stderr, fmt, a1, a2, a3);
279 fputc('\n', stderr);
280}