1 /* 2 * Copyright (c) 1992, Brian Berliner and Jeff Polk 3 * Copyright (c) 1989-1992, Brian Berliner 4 * 5 * You may distribute under the terms of the GNU General Public License as 6 * specified in the README file that comes with the CVS source distribution. 7 * 8 * Various useful functions for the CVS support code. 9 */ 10 11 #include "cvs.h" 12 #include "getline.h" 13 14 extern char *getlogin (); 15 16 /* 17 * malloc some data and die if it fails 18 */ 19 void * 20 xmalloc (bytes) 21 size_t bytes; 22 { 23 char *cp; 24 25 /* Parts of CVS try to xmalloc zero bytes and then free it. Some 26 systems have a malloc which returns NULL for zero byte 27 allocations but a free which can't handle NULL, so compensate. */ 28 if (bytes == 0) 29 bytes = 1; 30 31 cp = malloc (bytes); 32 if (cp == NULL) 33 { 34 char buf[80]; 35 sprintf (buf, "out of memory; can not allocate %lu bytes", 36 (unsigned long) bytes); 37 error (1, 0, buf); 38 } 39 return (cp); 40 } 41 42 /* 43 * realloc data and die if it fails [I've always wanted to have "realloc" do 44 * a "malloc" if the argument is NULL, but you can't depend on it. Here, I 45 * can *force* it. 46 */ 47 void * 48 xrealloc (ptr, bytes) 49 void *ptr; 50 size_t bytes; 51 { 52 char *cp; 53 54 if (!ptr) 55 cp = malloc (bytes); 56 else 57 cp = realloc (ptr, bytes); 58 59 if (cp == NULL) 60 { 61 char buf[80]; 62 sprintf (buf, "out of memory; can not reallocate %lu bytes", 63 (unsigned long) bytes); 64 error (1, 0, buf); 65 } 66 return (cp); 67 } 68 69 /* Two constants which tune expand_string. Having MIN_INCR as large 70 as 1024 might waste a bit of memory, but it shouldn't be too bad 71 (CVS used to allocate arrays of, say, 3000, PATH_MAX (8192, often), 72 or other such sizes). Probably anything which is going to allocate 73 memory which is likely to get as big as MAX_INCR shouldn't be doing 74 it in one block which must be contiguous, but since getrcskey does 75 so, we might as well limit the wasted memory to MAX_INCR or so 76 bytes. 77 78 MIN_INCR and MAX_INCR should both be powers of two and we generally 79 try to keep our allocations to powers of two for the most part. 80 Most malloc implementations these days tend to like that. */ 81 82 #define MIN_INCR 1024 83 #define MAX_INCR (2*1024*1024) 84 85 /* *STRPTR is a pointer returned from malloc (or NULL), pointing to *N 86 characters of space. Reallocate it so that points to at least 87 NEWSIZE bytes of space. Gives a fatal error if out of memory; 88 if it returns it was successful. */ 89 void 90 expand_string (strptr, n, newsize) 91 char **strptr; 92 size_t *n; 93 size_t newsize; 94 { 95 if (*n < newsize) 96 { 97 while (*n < newsize) 98 { 99 if (*n < MIN_INCR) 100 *n = MIN_INCR; 101 else if (*n >= MAX_INCR) 102 *n += MAX_INCR; 103 else 104 { 105 *n *= 2; 106 if (*n > MAX_INCR) 107 *n = MAX_INCR; 108 } 109 } 110 *strptr = xrealloc (*strptr, *n); 111 } 112 } 113 114 /* 115 * Duplicate a string, calling xmalloc to allocate some dynamic space 116 */ 117 char * 118 xstrdup (str) 119 const char *str; 120 { 121 char *s; 122 123 if (str == NULL) 124 return ((char *) NULL); 125 s = xmalloc (strlen (str) + 1); 126 (void) strcpy (s, str); 127 return (s); 128 } 129 130 /* Remove trailing newlines from STRING, destructively. */ 131 void 132 strip_trailing_newlines (str) 133 char *str; 134 { 135 int len; 136 len = strlen (str) - 1; 137 138 while (str[len] == '\n') 139 str[len--] = '\0'; 140 } 141 142 /* Return the number of levels that path ascends above where it starts. 143 For example: 144 "../../foo" -> 2 145 "foo/../../bar" -> 1 146 */ 147 /* FIXME: Should be using ISDIRSEP, last_component, or some other 148 mechanism which is more general than just looking at slashes, 149 particularly for the client.c caller. The server.c caller might 150 want something different, so be careful. */ 151 int 152 pathname_levels (path) 153 char *path; 154 { 155 char *p; 156 char *q; 157 int level; 158 int max_level; 159 160 max_level = 0; 161 p = path; 162 level = 0; 163 do 164 { 165 q = strchr (p, '/'); 166 if (q != NULL) 167 ++q; 168 if (p[0] == '.' && p[1] == '.' && (p[2] == '\0' || p[2] == '/')) 169 { 170 --level; 171 if (-level > max_level) 172 max_level = -level; 173 } 174 else if (p[0] == '\0' || p[0] == '/' || 175 (p[0] == '.' && (p[1] == '\0' || p[1] == '/'))) 176 ; 177 else 178 ++level; 179 p = q; 180 } while (p != NULL); 181 return max_level; 182 } 183 184 185 /* Free a vector, where (*ARGV)[0], (*ARGV)[1], ... (*ARGV)[*PARGC - 1] 186 are malloc'd and so is *ARGV itself. Such a vector is allocated by 187 line2argv or expand_wild, for example. */ 188 void 189 free_names (pargc, argv) 190 int *pargc; 191 char **argv; 192 { 193 register int i; 194 195 for (i = 0; i < *pargc; i++) 196 { /* only do through *pargc */ 197 free (argv[i]); 198 } 199 free (argv); 200 *pargc = 0; /* and set it to zero when done */ 201 } 202 203 /* Convert LINE into arguments separated by SEPCHARS. Set *ARGC 204 to the number of arguments found, and (*ARGV)[0] to the first argument, 205 (*ARGV)[1] to the second, etc. *ARGV is malloc'd and so are each of 206 (*ARGV)[0], (*ARGV)[1], ... Use free_names() to return the memory 207 allocated here back to the free pool. */ 208 void 209 line2argv (pargc, argv, line, sepchars) 210 int *pargc; 211 char ***argv; 212 char *line; 213 char *sepchars; 214 { 215 char *cp; 216 /* Could make a case for size_t or some other unsigned type, but 217 we'll stick with int to avoid signed/unsigned warnings when 218 comparing with *pargc. */ 219 int argv_allocated; 220 221 /* Small for testing. */ 222 argv_allocated = 1; 223 *argv = (char **) xmalloc (argv_allocated * sizeof (**argv)); 224 225 *pargc = 0; 226 for (cp = strtok (line, sepchars); cp; cp = strtok ((char *) NULL, sepchars)) 227 { 228 if (*pargc == argv_allocated) 229 { 230 argv_allocated *= 2; 231 *argv = xrealloc (*argv, argv_allocated * sizeof (**argv)); 232 } 233 (*argv)[*pargc] = xstrdup (cp); 234 (*pargc)++; 235 } 236 } 237 238 /* 239 * Returns the number of dots ('.') found in an RCS revision number 240 */ 241 int 242 numdots (s) 243 const char *s; 244 { 245 int dots = 0; 246 247 for (; *s; s++) 248 { 249 if (*s == '.') 250 dots++; 251 } 252 return (dots); 253 } 254 255 /* Compare revision numbers REV1 and REV2 by consecutive fields. 256 Return negative, zero, or positive in the manner of strcmp. The 257 two revision numbers must have the same number of fields, or else 258 compare_revnums will return an inaccurate result. */ 259 int 260 compare_revnums (rev1, rev2) 261 const char *rev1; 262 const char *rev2; 263 { 264 const char *s, *sp; 265 const char *t, *tp; 266 char *snext, *tnext; 267 int result = 0; 268 269 sp = s = rev1; 270 tp = t = rev2; 271 while (result == 0) 272 { 273 result = strtoul (sp, &snext, 10) - strtoul (tp, &tnext, 10); 274 if (*snext == '\0' || *tnext == '\0') 275 break; 276 sp = snext + 1; 277 tp = tnext + 1; 278 } 279 280 return result; 281 } 282 283 char * 284 increment_revnum (rev) 285 const char *rev; 286 { 287 char *newrev, *p; 288 int lastfield; 289 size_t len = strlen (rev); 290 291 newrev = (char *) xmalloc (len + 2); 292 memcpy (newrev, rev, len + 1); 293 p = strrchr (newrev, '.'); 294 if (p == NULL) 295 { 296 free (newrev); 297 return NULL; 298 } 299 lastfield = atoi (++p); 300 sprintf (p, "%d", lastfield + 1); 301 302 return newrev; 303 } 304 305 /* Return the username by which the caller should be identified in 306 CVS, in contexts such as the author field of RCS files, various 307 logs, etc. */ 308 char * 309 getcaller () 310 { 311 #ifndef SYSTEM_GETCALLER 312 static char *cache; 313 struct passwd *pw; 314 uid_t uid; 315 #endif 316 317 /* If there is a CVS username, return it. */ 318 #ifdef AUTH_SERVER_SUPPORT 319 if (CVS_Username != NULL) 320 return CVS_Username; 321 #endif 322 323 #ifdef SYSTEM_GETCALLER 324 return SYSTEM_GETCALLER (); 325 #else 326 /* Get the caller's login from his uid. If the real uid is "root" 327 try LOGNAME USER or getlogin(). If getlogin() and getpwuid() 328 both fail, return the uid as a string. */ 329 330 if (cache != NULL) 331 return cache; 332 333 uid = getuid (); 334 if (uid == (uid_t) 0) 335 { 336 char *name; 337 338 /* super-user; try getlogin() to distinguish */ 339 if (((name = getlogin ()) || (name = getenv("LOGNAME")) || 340 (name = getenv("USER"))) && *name) 341 { 342 cache = xstrdup (name); 343 return cache; 344 } 345 } 346 if ((pw = (struct passwd *) getpwuid (uid)) == NULL) 347 { 348 char uidname[20]; 349 350 (void) sprintf (uidname, "uid%lu", (unsigned long) uid); 351 cache = xstrdup (uidname); 352 return cache; 353 } 354 cache = xstrdup (pw->pw_name); 355 return cache; 356 #endif 357 } 358 359 #ifdef lint 360 #ifndef __GNUC__ 361 /* ARGSUSED */ 362 time_t 363 get_date (date, now) 364 char *date; 365 struct timeb *now; 366 { 367 time_t foo = 0; 368 369 return (foo); 370 } 371 #endif 372 #endif 373 374 /* Given two revisions, find their greatest common ancestor. If the 375 two input revisions exist, then rcs guarantees that the gca will 376 exist. */ 377 378 char * 379 gca (rev1, rev2) 380 const char *rev1; 381 const char *rev2; 382 { 383 int dots; 384 char *gca; 385 const char *p[2]; 386 int j[2]; 387 char *retval; 388 389 if (rev1 == NULL || rev2 == NULL) 390 { 391 error (0, 0, "sanity failure in gca"); 392 abort(); 393 } 394 395 /* The greatest common ancestor will have no more dots, and numbers 396 of digits for each component no greater than the arguments. Therefore 397 this string will be big enough. */ 398 gca = xmalloc (strlen (rev1) + strlen (rev2) + 100); 399 400 /* walk the strings, reading the common parts. */ 401 gca[0] = '\0'; 402 p[0] = rev1; 403 p[1] = rev2; 404 do 405 { 406 int i; 407 char c[2]; 408 char *s[2]; 409 410 for (i = 0; i < 2; ++i) 411 { 412 /* swap out the dot */ 413 s[i] = strchr (p[i], '.'); 414 if (s[i] != NULL) { 415 c[i] = *s[i]; 416 } 417 418 /* read an int */ 419 j[i] = atoi (p[i]); 420 421 /* swap back the dot... */ 422 if (s[i] != NULL) { 423 *s[i] = c[i]; 424 p[i] = s[i] + 1; 425 } 426 else 427 { 428 /* or mark us at the end */ 429 p[i] = NULL; 430 } 431 432 } 433 434 /* use the lowest. */ 435 (void) sprintf (gca + strlen (gca), "%d.", 436 j[0] < j[1] ? j[0] : j[1]); 437 438 } while (j[0] == j[1] 439 && p[0] != NULL 440 && p[1] != NULL); 441 442 /* back up over that last dot. */ 443 gca[strlen(gca) - 1] = '\0'; 444 445 /* numbers differ, or we ran out of strings. we're done with the 446 common parts. */ 447 448 dots = numdots (gca); 449 if (dots == 0) 450 { 451 /* revisions differ in trunk major number. */ 452 453 char *q; 454 const char *s; 455 456 s = (j[0] < j[1]) ? p[0] : p[1]; 457 458 if (s == NULL) 459 { 460 /* we only got one number. this is strange. */ 461 error (0, 0, "bad revisions %s or %s", rev1, rev2); 462 abort(); 463 } 464 else 465 { 466 /* we have a minor number. use it. */ 467 q = gca + strlen (gca); 468 469 *q++ = '.'; 470 for ( ; *s != '.' && *s != '\0'; ) 471 *q++ = *s++; 472 473 *q = '\0'; 474 } 475 } 476 else if ((dots & 1) == 0) 477 { 478 /* if we have an even number of dots, then we have a branch. 479 remove the last number in order to make it a revision. */ 480 481 char *s; 482 483 s = strrchr(gca, '.'); 484 *s = '\0'; 485 } 486 487 retval = xstrdup (gca); 488 free (gca); 489 return retval; 490 } 491 492 /* Give fatal error if REV is numeric and ARGC,ARGV imply we are 493 planning to operate on more than one file. The current directory 494 should be the working directory. Note that callers assume that we 495 will only be checking the first character of REV; it need not have 496 '\0' at the end of the tag name and other niceties. Right now this 497 is only called from admin.c, but if people like the concept it probably 498 should also be called from diff -r, update -r, get -r, and log -r. */ 499 500 void 501 check_numeric (rev, argc, argv) 502 const char *rev; 503 int argc; 504 char **argv; 505 { 506 if (rev == NULL || !isdigit ((unsigned char) *rev)) 507 return; 508 509 /* Note that the check for whether we are processing more than one 510 file is (basically) syntactic; that is, we don't behave differently 511 depending on whether a directory happens to contain only a single 512 file or whether it contains more than one. I strongly suspect this 513 is the least confusing behavior. */ 514 if (argc != 1 515 || (!wrap_name_has (argv[0], WRAP_TOCVS) && isdir (argv[0]))) 516 { 517 error (0, 0, "while processing more than one file:"); 518 error (1, 0, "attempt to specify a numeric revision"); 519 } 520 } 521 522 /* 523 * Sanity checks and any required fix-up on message passed to RCS via '-m'. 524 * RCS 5.7 requires that a non-total-whitespace, non-null message be provided 525 * with '-m'. Returns a newly allocated, non-empty buffer with whitespace 526 * stripped from end of lines and end of buffer. 527 * 528 * TODO: We no longer use RCS to manage repository files, so maybe this 529 * nonsense about non-empty log fields can be dropped. 530 */ 531 char * 532 make_message_rcslegal (message) 533 char *message; 534 { 535 char *dst, *dp, *mp; 536 537 if (message == NULL) message = ""; 538 539 /* Strip whitespace from end of lines and end of string. */ 540 dp = dst = (char *) xmalloc (strlen (message) + 1); 541 for (mp = message; *mp != '\0'; ++mp) 542 { 543 if (*mp == '\n') 544 { 545 /* At end-of-line; backtrack to last non-space. */ 546 while (dp > dst && (dp[-1] == ' ' || dp[-1] == '\t')) 547 --dp; 548 } 549 *dp++ = *mp; 550 } 551 552 /* Backtrack to last non-space at end of string, and truncate. */ 553 while (dp > dst && isspace ((unsigned char) dp[-1])) 554 --dp; 555 *dp = '\0'; 556 557 /* After all that, if there was no non-space in the string, 558 substitute a non-empty message. */ 559 if (*dst == '\0') 560 { 561 free (dst); 562 dst = xstrdup ("*** empty log message ***"); 563 } 564 565 return dst; 566 } 567 568 /* Does the file FINFO contain conflict markers? The whole concept 569 of looking at the contents of the file to figure out whether there are 570 unresolved conflicts is kind of bogus (people do want to manage files 571 which contain those patterns not as conflict markers), but for now it 572 is what we do. */ 573 int 574 file_has_markers (finfo) 575 const struct file_info *finfo; 576 { 577 FILE *fp; 578 char *line = NULL; 579 size_t line_allocated = 0; 580 int result; 581 582 result = 0; 583 fp = CVS_FOPEN (finfo->file, "r"); 584 if (fp == NULL) 585 error (1, errno, "cannot open %s", finfo->fullname); 586 while (getline (&line, &line_allocated, fp) > 0) 587 { 588 if (strncmp (line, RCS_MERGE_PAT_1, sizeof RCS_MERGE_PAT_1 - 1) == 0 || 589 strncmp (line, RCS_MERGE_PAT_2, sizeof RCS_MERGE_PAT_2 - 1) == 0 || 590 strncmp (line, RCS_MERGE_PAT_3, sizeof RCS_MERGE_PAT_3 - 1) == 0) 591 { 592 result = 1; 593 goto out; 594 } 595 } 596 if (ferror (fp)) 597 error (0, errno, "cannot read %s", finfo->fullname); 598 out: 599 if (fclose (fp) < 0) 600 error (0, errno, "cannot close %s", finfo->fullname); 601 if (line != NULL) 602 free (line); 603 return result; 604 } 605 606 /* Read the entire contents of the file NAME into *BUF. 607 If NAME is NULL, read from stdin. *BUF 608 is a pointer returned from malloc (or NULL), pointing to *BUFSIZE 609 bytes of space. The actual size is returned in *LEN. On error, 610 give a fatal error. The name of the file to use in error messages 611 (typically will include a directory if we have changed directory) 612 is FULLNAME. MODE is "r" for text or "rb" for binary. */ 613 614 void 615 get_file (name, fullname, mode, buf, bufsize, len) 616 const char *name; 617 const char *fullname; 618 const char *mode; 619 char **buf; 620 size_t *bufsize; 621 size_t *len; 622 { 623 struct stat s; 624 size_t nread; 625 char *tobuf; 626 FILE *e; 627 size_t filesize; 628 629 if (name == NULL) 630 { 631 e = stdin; 632 filesize = 100; /* force allocation of minimum buffer */ 633 } 634 else 635 { 636 /* Although it would be cleaner in some ways to just read 637 until end of file, reallocating the buffer, this function 638 does get called on files in the working directory which can 639 be of arbitrary size, so I think we better do all that 640 extra allocation. */ 641 642 if (CVS_STAT (name, &s) < 0) 643 error (1, errno, "can't stat %s", fullname); 644 645 /* Convert from signed to unsigned. */ 646 filesize = s.st_size; 647 648 e = open_file (name, mode); 649 } 650 651 if (*buf == NULL || *bufsize <= filesize) 652 { 653 *bufsize = filesize + 1; 654 *buf = xrealloc (*buf, *bufsize); 655 } 656 657 tobuf = *buf; 658 nread = 0; 659 while (1) 660 { 661 size_t got; 662 663 got = fread (tobuf, 1, *bufsize - (tobuf - *buf), e); 664 if (ferror (e)) 665 error (1, errno, "can't read %s", fullname); 666 nread += got; 667 tobuf += got; 668 669 if (feof (e)) 670 break; 671 672 /* Allocate more space if needed. */ 673 if (tobuf == *buf + *bufsize) 674 { 675 int c; 676 long off; 677 678 c = getc (e); 679 if (c == EOF) 680 break; 681 off = tobuf - *buf; 682 expand_string (buf, bufsize, *bufsize + 100); 683 tobuf = *buf + off; 684 *tobuf++ = c; 685 ++nread; 686 } 687 } 688 689 if (e != stdin && fclose (e) < 0) 690 error (0, errno, "cannot close %s", fullname); 691 692 *len = nread; 693 694 /* Force *BUF to be large enough to hold a null terminator. */ 695 if (nread == *bufsize) 696 expand_string (buf, bufsize, *bufsize + 1); 697 (*buf)[nread] = '\0'; 698 } 699 700 701 /* Follow a chain of symbolic links to its destination. FILENAME 702 should be a handle to a malloc'd block of memory which contains the 703 beginning of the chain. This routine will replace the contents of 704 FILENAME with the destination (a real file). */ 705 706 void 707 resolve_symlink (filename) 708 char **filename; 709 { 710 if ((! filename) || (! *filename)) 711 return; 712 713 while (islink (*filename)) 714 { 715 char *newname; 716 #ifdef HAVE_READLINK 717 /* The clean thing to do is probably to have each filesubr.c 718 implement this (with an error if not supported by the 719 platform, in which case islink would presumably return 0). 720 But that would require editing each filesubr.c and so the 721 expedient hack seems to be looking at HAVE_READLINK. */ 722 newname = xreadlink (*filename); 723 #else 724 error (1, 0, "internal error: islink doesn't like readlink"); 725 #endif 726 727 if (isabsolute (newname)) 728 { 729 free (*filename); 730 *filename = newname; 731 } 732 else 733 { 734 char *oldname = last_component (*filename); 735 int dirlen = oldname - *filename; 736 char *fullnewname = xmalloc (dirlen + strlen (newname) + 1); 737 strncpy (fullnewname, *filename, dirlen); 738 strcpy (fullnewname + dirlen, newname); 739 free (newname); 740 free (*filename); 741 *filename = fullnewname; 742 } 743 } 744 } 745 746 /* 747 * Rename a file to an appropriate backup name based on BAKPREFIX. 748 * If suffix non-null, then ".<suffix>" is appended to the new name. 749 * 750 * Returns the new name, which caller may free() if desired. 751 */ 752 char * 753 backup_file (filename, suffix) 754 const char *filename; 755 const char *suffix; 756 { 757 char *backup_name; 758 759 if (suffix == NULL) 760 { 761 backup_name = xmalloc (sizeof (BAKPREFIX) + strlen (filename) + 1); 762 sprintf (backup_name, "%s%s", BAKPREFIX, filename); 763 } 764 else 765 { 766 backup_name = xmalloc (sizeof (BAKPREFIX) 767 + strlen (filename) 768 + strlen (suffix) 769 + 2); /* one for dot, one for trailing '\0' */ 770 sprintf (backup_name, "%s%s.%s", BAKPREFIX, filename, suffix); 771 } 772 773 if (isfile (filename)) 774 copy_file (filename, backup_name); 775 776 return backup_name; 777 } 778 779