fixed typo
[rsync/rsync.git] / util.c
1 /* 
2    Copyright (C) Andrew Tridgell 1996
3    Copyright (C) Paul Mackerras 1996
4    
5    This program is free software; you can redistribute it and/or modify
6    it under the terms of the GNU General Public License as published by
7    the Free Software Foundation; either version 2 of the License, or
8    (at your option) any later version.
9    
10    This program is distributed in the hope that it will be useful,
11    but WITHOUT ANY WARRANTY; without even the implied warranty of
12    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13    GNU General Public License for more details.
14    
15    You should have received a copy of the GNU General Public License
16    along with this program; if not, write to the Free Software
17    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18 */
19
20 /*
21   Utilities used in rsync 
22
23   tridge, June 1996
24   */
25 #include "rsync.h"
26
27 /****************************************************************************
28 Set a fd into nonblocking mode. Uses POSIX O_NONBLOCK if available,
29 else
30 if SYSV use O_NDELAY
31 if BSD use FNDELAY
32 ****************************************************************************/
33 int set_nonblocking(int fd)
34 {
35         int val;
36 #ifdef O_NONBLOCK
37 #define FLAG_TO_SET O_NONBLOCK
38 #else
39 #ifdef SYSV
40 #define FLAG_TO_SET O_NDELAY
41 #else /* BSD */
42 #define FLAG_TO_SET FNDELAY
43 #endif
44 #endif
45         
46         if((val = fcntl(fd, F_GETFL, 0)) == -1)
47                 return -1;
48         val |= FLAG_TO_SET;
49         return fcntl( fd, F_SETFL, val);
50 #undef FLAG_TO_SET
51 }
52
53
54 /* this is taken from CVS */
55 int piped_child(char **command,int *f_in,int *f_out)
56 {
57   int pid;
58   int to_child_pipe[2];
59   int from_child_pipe[2];
60
61   if (pipe(to_child_pipe) < 0 ||
62       pipe(from_child_pipe) < 0) {
63     rprintf(FERROR,"pipe: %s\n",strerror(errno));
64     exit_cleanup(RERR_IPC);
65   }
66
67
68   pid = do_fork();
69   if (pid < 0) {
70     rprintf(FERROR,"fork: %s\n",strerror(errno));
71     exit_cleanup(RERR_IPC);
72   }
73
74   if (pid == 0)
75     {
76       extern int orig_umask;
77       if (dup2(to_child_pipe[0], STDIN_FILENO) < 0 ||
78           close(to_child_pipe[1]) < 0 ||
79           close(from_child_pipe[0]) < 0 ||
80           dup2(from_child_pipe[1], STDOUT_FILENO) < 0) {
81         rprintf(FERROR,"Failed to dup/close : %s\n",strerror(errno));
82         exit_cleanup(RERR_IPC);
83       }
84       if (to_child_pipe[0] != STDIN_FILENO) close(to_child_pipe[0]);
85       if (from_child_pipe[1] != STDOUT_FILENO) close(from_child_pipe[1]);
86       umask(orig_umask);
87       execvp(command[0], command);
88       rprintf(FERROR,"Failed to exec %s : %s\n",
89               command[0],strerror(errno));
90       exit_cleanup(RERR_IPC);
91     }
92
93   if (close(from_child_pipe[1]) < 0 ||
94       close(to_child_pipe[0]) < 0) {
95     rprintf(FERROR,"Failed to close : %s\n",strerror(errno));   
96     exit_cleanup(RERR_IPC);
97   }
98
99   *f_in = from_child_pipe[0];
100   *f_out = to_child_pipe[1];
101
102   set_nonblocking(*f_in);
103   set_nonblocking(*f_out);
104   
105   return pid;
106 }
107
108 int local_child(int argc, char **argv,int *f_in,int *f_out)
109 {
110         int pid;
111         int to_child_pipe[2];
112         int from_child_pipe[2];
113
114         if (pipe(to_child_pipe) < 0 ||
115             pipe(from_child_pipe) < 0) {
116                 rprintf(FERROR,"pipe: %s\n",strerror(errno));
117                 exit_cleanup(RERR_IPC);
118         }
119
120
121         pid = do_fork();
122         if (pid < 0) {
123                 rprintf(FERROR,"fork: %s\n",strerror(errno));
124                 exit_cleanup(RERR_IPC);
125         }
126
127         if (pid == 0) {
128                 extern int am_sender;
129                 extern int am_server;
130
131                 am_sender = !am_sender;
132                 am_server = 1;          
133
134                 if (dup2(to_child_pipe[0], STDIN_FILENO) < 0 ||
135                     close(to_child_pipe[1]) < 0 ||
136                     close(from_child_pipe[0]) < 0 ||
137                     dup2(from_child_pipe[1], STDOUT_FILENO) < 0) {
138                         rprintf(FERROR,"Failed to dup/close : %s\n",strerror(errno));
139                         exit_cleanup(RERR_IPC);
140                 }
141                 if (to_child_pipe[0] != STDIN_FILENO) close(to_child_pipe[0]);
142                 if (from_child_pipe[1] != STDOUT_FILENO) close(from_child_pipe[1]);
143                 start_server(STDIN_FILENO, STDOUT_FILENO, argc, argv);
144         }
145
146         if (close(from_child_pipe[1]) < 0 ||
147             close(to_child_pipe[0]) < 0) {
148                 rprintf(FERROR,"Failed to close : %s\n",strerror(errno));   
149                 exit_cleanup(RERR_IPC);
150         }
151
152         *f_in = from_child_pipe[0];
153         *f_out = to_child_pipe[1];
154   
155         return pid;
156 }
157
158
159
160 void out_of_memory(char *str)
161 {
162   rprintf(FERROR,"ERROR: out of memory in %s\n",str);
163   exit_cleanup(RERR_MALLOC);
164 }
165
166 void overflow(char *str)
167 {
168   rprintf(FERROR,"ERROR: buffer overflow in %s\n",str);
169   exit_cleanup(RERR_MALLOC);
170 }
171
172
173
174 int set_modtime(char *fname,time_t modtime)
175 {
176         extern int dry_run;
177         if (dry_run) return 0;
178         {
179 #ifdef HAVE_UTIMBUF
180                 struct utimbuf tbuf;  
181                 tbuf.actime = time(NULL);
182                 tbuf.modtime = modtime;
183                 return utime(fname,&tbuf);
184 #elif defined(HAVE_UTIME)
185                 time_t t[2];
186                 t[0] = time(NULL);
187                 t[1] = modtime;
188                 return utime(fname,t);
189 #else
190                 struct timeval t[2];
191                 t[0].tv_sec = time(NULL);
192                 t[0].tv_usec = 0;
193                 t[1].tv_sec = modtime;
194                 t[1].tv_usec = 0;
195                 return utimes(fname,t);
196 #endif
197         }
198 }
199
200
201 /****************************************************************************
202 create any necessary directories in fname. Unfortunately we don't know
203 what perms to give the directory when this is called so we need to rely
204 on the umask
205 ****************************************************************************/
206 int create_directory_path(char *fname)
207 {
208         extern int orig_umask;
209         char *p;
210
211         while (*fname == '/') fname++;
212         while (strncmp(fname,"./",2)==0) fname += 2;
213
214         p = fname;
215         while ((p=strchr(p,'/'))) {
216                 *p = 0;
217                 do_mkdir(fname,0777 & ~orig_umask); 
218                 *p = '/';
219                 p++;
220         }
221         return 0;
222 }
223
224
225 /* Write LEN bytes at PTR to descriptor DESC, retrying if interrupted.
226    Return LEN upon success, write's (negative) error code otherwise.  
227
228    derived from GNU C's cccp.c.
229 */
230 static int full_write(int desc, char *ptr, int len)
231 {
232         int total_written;
233         
234         total_written = 0;
235         while (len > 0) {
236                 int written = write (desc, ptr, len);
237                 if (written < 0)  {
238 #ifdef EINTR
239                         if (errno == EINTR)
240                                 continue;
241 #endif
242                         return written;
243                 }
244                 total_written += written;
245                 ptr += written;
246                 len -= written;
247         }
248         return total_written;
249 }
250
251 /* Read LEN bytes at PTR from descriptor DESC, retrying if interrupted.
252    Return the actual number of bytes read, zero for EOF, or negative
253    for an error.  
254
255    derived from GNU C's cccp.c. */
256 static int safe_read(int desc, char *ptr, int len)
257 {
258         int n_chars;
259  
260         if (len <= 0)
261                 return len;
262  
263 #ifdef EINTR
264         do {
265                 n_chars = read(desc, ptr, len);
266         } while (n_chars < 0 && errno == EINTR);
267 #else
268         n_chars = read(desc, ptr, len);
269 #endif
270  
271         return n_chars;
272 }
273
274
275 /* copy a file - this is used in conjunction with the --temp-dir option */
276 int copy_file(char *source, char *dest, mode_t mode)
277 {
278         int ifd;
279         int ofd;
280         char buf[1024 * 8];
281         int len;   /* Number of bytes read into `buf'. */
282
283         ifd = open(source, O_RDONLY);
284         if (ifd == -1) {
285                 rprintf(FERROR,"open %s: %s\n",
286                         source,strerror(errno));
287                 return -1;
288         }
289
290         if (do_unlink(dest) && errno != ENOENT) {
291                 rprintf(FERROR,"unlink %s: %s\n",
292                         dest,strerror(errno));
293                 return -1;
294         }
295
296         ofd = do_open(dest, O_WRONLY | O_CREAT | O_TRUNC | O_EXCL, mode);
297         if (ofd == -1) {
298                 rprintf(FERROR,"open %s: %s\n",
299                         dest,strerror(errno));
300                 close(ifd);
301                 return -1;
302         }
303
304         while ((len = safe_read(ifd, buf, sizeof(buf))) > 0) {
305                 if (full_write(ofd, buf, len) < 0) {
306                         rprintf(FERROR,"write %s: %s\n",
307                                 dest,strerror(errno));
308                         close(ifd);
309                         close(ofd);
310                         return -1;
311                 }
312         }
313
314         close(ifd);
315         close(ofd);
316
317         if (len < 0) {
318                 rprintf(FERROR,"read %s: %s\n",
319                         source,strerror(errno));
320                 return -1;
321         }
322
323         return 0;
324 }
325
326 /* sleep for a while via select */
327 void u_sleep(int usec)
328 {
329         struct timeval tv;
330
331         tv.tv_sec = 0;
332         tv.tv_usec = usec;
333         select(0, NULL, NULL, NULL, &tv);
334 }
335
336
337 static pid_t all_pids[10];
338 static int num_pids;
339
340 /* fork and record the pid of the child */
341 pid_t do_fork(void)
342 {
343         pid_t newpid = fork();
344         
345         if (newpid) {
346                 all_pids[num_pids++] = newpid;
347         }
348         return newpid;
349 }
350
351 /* kill all children */
352 void kill_all(int sig)
353 {
354         int i;
355         for (i=0;i<num_pids;i++) {
356                 if (all_pids[i] != getpid())
357                         kill(all_pids[i], sig);
358         }
359 }
360
361 /* like strncpy but does not 0 fill the buffer and always null 
362    terminates (thus it can use maxlen+1 space in d) */
363 void strlcpy(char *d, char *s, int maxlen)
364 {
365         int len = strlen(s);
366         if (len > maxlen) len = maxlen;
367         memcpy(d, s, len);
368         d[len] = 0;
369 }
370
371 /* like strncat but does not 0 fill the buffer and always null 
372    terminates (thus it can use maxlen+1 space in d) */
373 void strlcat(char *d, char *s, int maxlen)
374 {
375         int len1 = strlen(d);
376         int len2 = strlen(s);
377         if (len1+len2 > maxlen) {
378                 len2 = maxlen-len1;
379         }
380         if (len2 > 0) {
381                 memcpy(d+len1, s, len2);
382                 d[len1+len2] = 0;
383         }
384 }
385
386 /* turn a user name into a uid */
387 int name_to_uid(char *name, uid_t *uid)
388 {
389         struct passwd *pass;
390         if (!name || !*name) return 0;
391         pass = getpwnam(name);
392         if (pass) {
393                 *uid = pass->pw_uid;
394                 return 1;
395         }
396         return 0;
397 }
398
399 /* turn a group name into a gid */
400 int name_to_gid(char *name, gid_t *gid)
401 {
402         struct group *grp;
403         if (!name || !*name) return 0;
404         grp = getgrnam(name);
405         if (grp) {
406                 *gid = grp->gr_gid;
407                 return 1;
408         }
409         return 0;
410 }
411
412
413 /* lock a byte range in a open file */
414 int lock_range(int fd, int offset, int len)
415 {
416         struct flock lock;
417
418         lock.l_type = F_WRLCK;
419         lock.l_whence = SEEK_SET;
420         lock.l_start = offset;
421         lock.l_len = len;
422         lock.l_pid = 0;
423         
424         return fcntl(fd,F_SETLK,&lock) == 0;
425 }
426
427
428 static void glob_expand_one(char *s, char **argv, int *argc, int maxargs)
429 {
430 #if !(defined(HAVE_GLOB) && defined(HAVE_GLOB_H))
431         if (!*s) s = ".";
432         argv[*argc] = strdup(s);
433         (*argc)++;
434         return;
435 #else
436         glob_t globbuf;
437         int i;
438
439         if (!*s) s = ".";
440
441         argv[*argc] = strdup(s);
442
443         memset(&globbuf, 0, sizeof(globbuf));
444         glob(argv[*argc], 0, NULL, &globbuf);
445         if (globbuf.gl_pathc == 0) {
446                 (*argc)++;
447                 globfree(&globbuf);
448                 return;
449         }
450         for (i=0; i<(maxargs - (*argc)) && i<globbuf.gl_pathc;i++) {
451                 if (i == 0) free(argv[*argc]);
452                 argv[(*argc) + i] = strdup(globbuf.gl_pathv[i]);
453                 if (!argv[(*argc) + i]) out_of_memory("glob_expand");
454         }
455         globfree(&globbuf);
456         (*argc) += i;
457 #endif
458 }
459
460 void glob_expand(char *base1, char **argv, int *argc, int maxargs)
461 {
462         char *s = argv[*argc];
463         char *p, *q;
464         char *base = base1;
465
466         if (!s || !*s) return;
467
468         if (strncmp(s, base, strlen(base)) == 0) {
469                 s += strlen(base);
470         }
471
472         s = strdup(s);
473         if (!s) out_of_memory("glob_expand");
474
475         base = (char *)malloc(strlen(base1)+3);
476         if (!base) out_of_memory("glob_expand");
477
478         sprintf(base," %s/", base1);
479
480         q = s;
481         while ((p = strstr(q,base)) && ((*argc) < maxargs)) {
482                 /* split it at this point */
483                 *p = 0;
484                 glob_expand_one(q, argv, argc, maxargs);
485                 q = p+strlen(base);
486         }
487
488         if (*q && (*argc < maxargs)) glob_expand_one(q, argv, argc, maxargs);
489
490         free(s);
491         free(base);
492 }
493
494 /*******************************************************************
495   convert a string to lower case
496 ********************************************************************/
497 void strlower(char *s)
498 {
499         while (*s) {
500                 if (isupper(*s)) *s = tolower(*s);
501                 s++;
502         }
503 }
504
505 /* this is like vsnprintf but the 'n' limit does not include
506    the terminating null. So if you have a 1024 byte buffer then
507    pass 1023 for n */
508 int vslprintf(char *str, int n, const char *format, va_list ap)
509 {
510         int ret = vsnprintf(str, n, format, ap);
511         if (ret > n || ret < 0) {
512                 str[n] = 0;
513                 return -1;
514         }
515         str[ret] = 0;
516         return ret;
517 }
518
519
520 /* like snprintf but always null terminates */
521 int slprintf(char *str, int n, char *format, ...)
522 {
523         va_list ap;  
524         int ret;
525
526         va_start(ap, format);
527         ret = vslprintf(str,n,format,ap);
528         va_end(ap);
529         return ret;
530 }
531
532
533 void *Realloc(void *p, int size)
534 {
535         if (!p) return (void *)malloc(size);
536         return (void *)realloc(p, size);
537 }
538
539
540 void clean_fname(char *name)
541 {
542         char *p;
543         int l;
544         int modified = 1;
545
546         if (!name) return;
547
548         while (modified) {
549                 modified = 0;
550
551                 if ((p=strstr(name,"/./"))) {
552                         modified = 1;
553                         while (*p) {
554                                 p[0] = p[2];
555                                 p++;
556                         }
557                 }
558
559                 if ((p=strstr(name,"//"))) {
560                         modified = 1;
561                         while (*p) {
562                                 p[0] = p[1];
563                                 p++;
564                         }
565                 }
566
567                 if (strncmp(p=name,"./",2) == 0) {      
568                         modified = 1;
569                         do {
570                                 p[0] = p[2];
571                         } while (*p++);
572                 }
573
574                 l = strlen(p=name);
575                 if (l > 1 && p[l-1] == '/') {
576                         modified = 1;
577                         p[l-1] = 0;
578                 }
579         }
580 }
581
582 /*
583  * Make path appear as if a chroot had occurred:
584  *    0. call clean_fname on it.
585  *    1. remove leading "/" (or replace with "." if at end)
586  *    2. remove leading ".." components
587  *    3. delete any other "<dir>/.." (recursively)
588  * Return a malloc'ed copy.
589  * Contributed by Dave Dykstra <dwd@bell-labs.com>
590  */
591
592 char *sanitize_path(char *p)
593 {
594         char *copy, *copyp;
595
596         clean_fname(p);
597
598         copy = (char *) malloc(strlen(p)+1);
599         copyp = copy;
600         while (*p != '\0') {
601                 if ((*p == '/') && (copyp == copy)) {
602                         /* remove leading slash */
603                         p++;
604                 }
605                 else if ((*p == '.') && (*(p+1) == '.') &&
606                             ((*(p+2) == '/') || (*(p+2) == '\0'))) {
607                         /* remove .. followed by slash or end */
608                         p += 2;
609                         if (copyp != copy) {
610                                 /* backup the copy one level */
611                                 while ((--copyp != copy) && (*copyp == '/'))
612                                         /* skip trailing slashes */
613                                         ;
614                                 while ((copyp != copy) && (*copyp != '/'))
615                                         /* skip back through slash */
616                                         copyp--;
617                         }
618                 } else {
619                         /* copy one component */
620                         while (1) {
621                                 *copyp++ = *p++;
622                                 if ((*p == '\0') || (*(p-1) == '/'))
623                                         break;
624                         }
625                 }
626         }
627         *copyp = '\0';
628         return(copy);
629 }
630
631
632 static char curr_dir[MAXPATHLEN];
633
634 /* like chdir() but can be reversed with pop_dir() if save is set. It
635    is also much faster as it remembers where we have been */
636 char *push_dir(char *dir, int save)
637 {
638         char *ret = curr_dir;
639         static int initialised;
640
641         if (!initialised) {
642                 initialised = 1;
643                 getcwd(curr_dir, sizeof(curr_dir)-1);
644         }
645
646         if (chdir(dir)) return NULL;
647
648         if (save) {
649                 ret = strdup(curr_dir);
650         }
651
652         if (*dir == '/') {
653                 strlcpy(curr_dir, dir, sizeof(curr_dir)-1);
654         } else {
655                 strlcat(curr_dir,"/", sizeof(curr_dir)-1);
656                 strlcat(curr_dir,dir, sizeof(curr_dir)-1);
657         }
658
659         clean_fname(curr_dir);
660
661         return ret;
662 }
663
664 /* reverse a push_dir call */
665 int pop_dir(char *dir)
666 {
667         int ret;
668
669         ret = chdir(dir);
670         if (ret) {
671                 free(dir);
672                 return ret;
673         }
674
675         strlcpy(curr_dir, dir, sizeof(curr_dir)-1);
676
677         free(dir);
678
679         return 0;
680 }
681
682 /* we need to supply our own strcmp function for file list comparisons
683    to ensure that signed/unsigned usage is consistent between machines. */
684 int u_strcmp(const char *cs1, const char *cs2)
685 {
686         const uchar *s1 = (uchar *)cs1;
687         const uchar *s2 = (uchar *)cs2;
688
689         while (*s1 && *s2 && (*s1 == *s2)) {
690                 s1++; s2++;
691         }
692         
693         return (int)*s1 - (int)*s2;
694 }
695
696 static OFF_T last_ofs;
697
698 void end_progress(void)
699 {
700         extern int do_progress, am_server;
701
702         if (do_progress && !am_server) {
703                 rprintf(FINFO,"\n");
704         }
705         last_ofs = 0;
706 }
707
708 void show_progress(OFF_T ofs, OFF_T size)
709 {
710         extern int do_progress, am_server;
711
712         if (do_progress && !am_server) {
713                 if (ofs > last_ofs + 1000) {
714                         int pct = (int)((100.0*ofs)/size);
715                         rprintf(FINFO,"%.0f (%d%%)\r", (double)ofs, pct);
716                         last_ofs = ofs;
717                 }
718         }
719 }
720
721 /* determine if a symlink points outside the current directory tree */
722 int unsafe_symlink(char *dest, char *src)
723 {
724         char *tok;
725         int depth = 0;
726
727         /* all absolute and null symlinks are unsafe */
728         if (!dest || !(*dest) || (*dest == '/')) return 1;
729
730         src = strdup(src);
731         if (!src) out_of_memory("unsafe_symlink");
732
733         /* find out what our safety margin is */
734         for (tok=strtok(src,"/"); tok; tok=strtok(NULL,"/")) {
735                 if (strcmp(tok,"..") == 0) {
736                         depth=0;
737                 } else if (strcmp(tok,".") == 0) {
738                         /* nothing */
739                 } else {
740                         depth++;
741                 }
742         }
743         free(src);
744
745         /* drop by one to account for the filename portion */
746         depth--;
747
748         dest = strdup(dest);
749         if (!dest) out_of_memory("unsafe_symlink");
750
751         for (tok=strtok(dest,"/"); tok; tok=strtok(NULL,"/")) {
752                 if (strcmp(tok,"..") == 0) {
753                         depth--;
754                 } else if (strcmp(tok,".") == 0) {
755                         /* nothing */
756                 } else {
757                         depth++;
758                 }
759                 /* if at any point we go outside the current directory then
760                    stop - it is unsafe */
761                 if (depth < 0) break;
762         }
763
764         free(dest);
765         return (depth < 0);
766 }
767
768
769 /****************************************************************************
770   return the date and time as a string
771 ****************************************************************************/
772 char *timestring(time_t t)
773 {
774         static char TimeBuf[200];
775         struct tm *tm = localtime(&t);
776
777 #ifdef HAVE_STRFTIME
778         strftime(TimeBuf,sizeof(TimeBuf)-1,"%Y/%m/%d %T",tm);
779 #else
780         strlcpy(TimeBuf, asctime(tm), sizeof(TimeBuf)-1);
781 #endif
782
783         if (TimeBuf[strlen(TimeBuf)-1] == '\n') {
784                 TimeBuf[strlen(TimeBuf)-1] = 0;
785         }
786
787         return(TimeBuf);
788 }
789