recipient.c revision 38032
1/* 2 * Copyright (c) 1998 Sendmail, Inc. All rights reserved. 3 * Copyright (c) 1983, 1995-1997 Eric P. Allman. All rights reserved. 4 * Copyright (c) 1988, 1993 5 * The Regents of the University of California. All rights reserved. 6 * 7 * By using this file, you agree to the terms and conditions set 8 * forth in the LICENSE file which can be found at the top level of 9 * the sendmail distribution. 10 * 11 */ 12 13#ifndef lint 14static char sccsid[] = "@(#)recipient.c 8.154 (Berkeley) 6/24/98"; 15#endif /* not lint */ 16 17# include "sendmail.h" 18# include <grp.h> 19 20/* 21** SENDTOLIST -- Designate a send list. 22** 23** The parameter is a comma-separated list of people to send to. 24** This routine arranges to send to all of them. 25** 26** Parameters: 27** list -- the send list. 28** ctladdr -- the address template for the person to 29** send to -- effective uid/gid are important. 30** This is typically the alias that caused this 31** expansion. 32** sendq -- a pointer to the head of a queue to put 33** these people into. 34** aliaslevel -- the current alias nesting depth -- to 35** diagnose loops. 36** e -- the envelope in which to add these recipients. 37** 38** Returns: 39** The number of addresses actually on the list. 40** 41** Side Effects: 42** none. 43*/ 44 45/* q_flags bits inherited from ctladdr */ 46#define QINHERITEDBITS (QPINGONSUCCESS|QPINGONFAILURE|QPINGONDELAY|QHASNOTIFY) 47 48int 49sendtolist(list, ctladdr, sendq, aliaslevel, e) 50 char *list; 51 ADDRESS *ctladdr; 52 ADDRESS **sendq; 53 int aliaslevel; 54 register ENVELOPE *e; 55{ 56 register char *p; 57 register ADDRESS *al; /* list of addresses to send to */ 58 char delimiter; /* the address delimiter */ 59 int naddrs; 60 int i; 61 char *oldto = e->e_to; 62 char *bufp; 63 char buf[MAXNAME + 1]; 64 65 if (list == NULL) 66 { 67 syserr("sendtolist: null list"); 68 return 0; 69 } 70 71 if (tTd(25, 1)) 72 { 73 printf("sendto: %s\n ctladdr=", list); 74 printaddr(ctladdr, FALSE); 75 } 76 77 /* heuristic to determine old versus new style addresses */ 78 if (ctladdr == NULL && 79 (strchr(list, ',') != NULL || strchr(list, ';') != NULL || 80 strchr(list, '<') != NULL || strchr(list, '(') != NULL)) 81 e->e_flags &= ~EF_OLDSTYLE; 82 delimiter = ' '; 83 if (!bitset(EF_OLDSTYLE, e->e_flags) || ctladdr != NULL) 84 delimiter = ','; 85 86 al = NULL; 87 naddrs = 0; 88 89 /* make sure we have enough space to copy the string */ 90 i = strlen(list) + 1; 91 if (i <= sizeof buf) 92 bufp = buf; 93 else 94 bufp = xalloc(i); 95 strcpy(bufp, denlstring(list, FALSE, TRUE)); 96 97 for (p = bufp; *p != '\0'; ) 98 { 99 auto char *delimptr; 100 register ADDRESS *a; 101 102 /* parse the address */ 103 while ((isascii(*p) && isspace(*p)) || *p == ',') 104 p++; 105 a = parseaddr(p, NULLADDR, RF_COPYALL, delimiter, &delimptr, e); 106 p = delimptr; 107 if (a == NULL) 108 continue; 109 a->q_next = al; 110 a->q_alias = ctladdr; 111 112 /* arrange to inherit attributes from parent */ 113 if (ctladdr != NULL) 114 { 115 ADDRESS *b; 116 extern ADDRESS *self_reference __P((ADDRESS *, ENVELOPE *)); 117 118 /* self reference test */ 119 if (sameaddr(ctladdr, a)) 120 { 121 if (tTd(27, 5)) 122 { 123 printf("sendtolist: QSELFREF "); 124 printaddr(ctladdr, FALSE); 125 } 126 ctladdr->q_flags |= QSELFREF; 127 } 128 129 /* check for address loops */ 130 b = self_reference(a, e); 131 if (b != NULL) 132 { 133 b->q_flags |= QSELFREF; 134 if (tTd(27, 5)) 135 { 136 printf("sendtolist: QSELFREF "); 137 printaddr(b, FALSE); 138 } 139 if (a != b) 140 { 141 if (tTd(27, 5)) 142 { 143 printf("sendtolist: QDONTSEND "); 144 printaddr(a, FALSE); 145 } 146 a->q_flags |= QDONTSEND; 147 b->q_flags |= a->q_flags & QNOTREMOTE; 148 continue; 149 } 150 } 151 152 /* full name */ 153 if (a->q_fullname == NULL) 154 a->q_fullname = ctladdr->q_fullname; 155 156 /* various flag bits */ 157 a->q_flags &= ~QINHERITEDBITS; 158 a->q_flags |= ctladdr->q_flags & QINHERITEDBITS; 159 160 /* original recipient information */ 161 a->q_orcpt = ctladdr->q_orcpt; 162 } 163 164 al = a; 165 } 166 167 /* arrange to send to everyone on the local send list */ 168 while (al != NULL) 169 { 170 register ADDRESS *a = al; 171 172 al = a->q_next; 173 a = recipient(a, sendq, aliaslevel, e); 174 naddrs++; 175 } 176 177 e->e_to = oldto; 178 if (bufp != buf) 179 free(bufp); 180 return (naddrs); 181} 182/* 183** RECIPIENT -- Designate a message recipient 184** 185** Saves the named person for future mailing. 186** 187** Parameters: 188** a -- the (preparsed) address header for the recipient. 189** sendq -- a pointer to the head of a queue to put the 190** recipient in. Duplicate supression is done 191** in this queue. 192** aliaslevel -- the current alias nesting depth. 193** e -- the current envelope. 194** 195** Returns: 196** The actual address in the queue. This will be "a" if 197** the address is not a duplicate, else the original address. 198** 199** Side Effects: 200** none. 201*/ 202 203ADDRESS * 204recipient(a, sendq, aliaslevel, e) 205 register ADDRESS *a; 206 register ADDRESS **sendq; 207 int aliaslevel; 208 register ENVELOPE *e; 209{ 210 register ADDRESS *q; 211 ADDRESS **pq; 212 register struct mailer *m; 213 register char *p; 214 bool quoted = FALSE; /* set if the addr has a quote bit */ 215 int findusercount = 0; 216 bool initialdontsend = bitset(QDONTSEND, a->q_flags); 217 int i; 218 char *buf; 219 char buf0[MAXNAME + 1]; /* unquoted image of the user name */ 220 extern void alias __P((ADDRESS *, ADDRESS **, int, ENVELOPE *)); 221 222 e->e_to = a->q_paddr; 223 m = a->q_mailer; 224 errno = 0; 225 if (aliaslevel == 0) 226 a->q_flags |= QPRIMARY; 227 if (tTd(26, 1)) 228 { 229 printf("\nrecipient (%d): ", aliaslevel); 230 printaddr(a, FALSE); 231 } 232 233 /* if this is primary, add it to the original recipient list */ 234 if (a->q_alias == NULL) 235 { 236 if (e->e_origrcpt == NULL) 237 e->e_origrcpt = a->q_paddr; 238 else if (e->e_origrcpt != a->q_paddr) 239 e->e_origrcpt = ""; 240 } 241 242 /* break aliasing loops */ 243 if (aliaslevel > MaxAliasRecursion) 244 { 245 a->q_flags |= QBADADDR; 246 a->q_status = "5.4.6"; 247 usrerr("554 aliasing/forwarding loop broken (%d aliases deep; %d max)", 248 aliaslevel, MaxAliasRecursion); 249 return (a); 250 } 251 252 /* 253 ** Finish setting up address structure. 254 */ 255 256 /* get unquoted user for file, program or user.name check */ 257 i = strlen(a->q_user); 258 if (i >= sizeof buf0) 259 buf = xalloc(i + 1); 260 else 261 buf = buf0; 262 (void) strcpy(buf, a->q_user); 263 for (p = buf; *p != '\0' && !quoted; p++) 264 { 265 if (*p == '\\') 266 quoted = TRUE; 267 } 268 stripquotes(buf); 269 270 /* check for direct mailing to restricted mailers */ 271 if (m == ProgMailer) 272 { 273 if (a->q_alias == NULL) 274 { 275 a->q_flags |= QBADADDR; 276 a->q_status = "5.7.1"; 277 usrerr("550 Cannot mail directly to programs"); 278 } 279 else if (bitset(QBOGUSSHELL, a->q_alias->q_flags)) 280 { 281 a->q_flags |= QBADADDR; 282 a->q_status = "5.7.1"; 283 if (a->q_alias->q_ruser == NULL) 284 usrerr("550 UID %d is an unknown user: cannot mail to programs", 285 a->q_alias->q_uid); 286 else 287 usrerr("550 User %s@%s doesn't have a valid shell for mailing to programs", 288 a->q_alias->q_ruser, MyHostName); 289 } 290 else if (bitset(QUNSAFEADDR, a->q_alias->q_flags)) 291 { 292 a->q_flags |= QBADADDR; 293 a->q_status = "5.7.1"; 294 a->q_rstatus = newstr("Unsafe for mailing to programs"); 295 usrerr("550 Address %s is unsafe for mailing to programs", 296 a->q_alias->q_paddr); 297 } 298 } 299 300 /* 301 ** Look up this person in the recipient list. 302 ** If they are there already, return, otherwise continue. 303 ** If the list is empty, just add it. Notice the cute 304 ** hack to make from addresses suppress things correctly: 305 ** the QDONTSEND bit will be set in the send list. 306 ** [Please note: the emphasis is on "hack."] 307 */ 308 309 for (pq = sendq; (q = *pq) != NULL; pq = &q->q_next) 310 { 311 if (sameaddr(q, a) && 312 (bitset(QRCPTOK, q->q_flags) || 313 !bitset(QPRIMARY, q->q_flags))) 314 { 315 if (tTd(26, 1)) 316 { 317 printf("%s in sendq: ", a->q_paddr); 318 printaddr(q, FALSE); 319 } 320 if (!bitset(QPRIMARY, q->q_flags)) 321 { 322 if (!bitset(QDONTSEND, a->q_flags)) 323 message("duplicate suppressed"); 324 q->q_flags |= a->q_flags; 325 } 326 else if (bitset(QSELFREF, q->q_flags)) 327 q->q_flags |= a->q_flags & ~QDONTSEND; 328 a = q; 329 goto done; 330 } 331 } 332 333 /* add address on list */ 334 *pq = a; 335 a->q_next = NULL; 336 337 /* 338 ** Alias the name and handle special mailer types. 339 */ 340 341 trylocaluser: 342 if (tTd(29, 7)) 343 printf("at trylocaluser %s\n", a->q_user); 344 345 if (bitset(QDONTSEND|QBADADDR|QVERIFIED, a->q_flags)) 346 goto testselfdestruct; 347 348 if (m == InclMailer) 349 { 350 a->q_flags |= QDONTSEND; 351 if (a->q_alias == NULL) 352 { 353 a->q_flags |= QBADADDR; 354 a->q_status = "5.7.1"; 355 usrerr("550 Cannot mail directly to :include:s"); 356 } 357 else 358 { 359 int ret; 360 361 message("including file %s", a->q_user); 362 ret = include(a->q_user, FALSE, a, sendq, aliaslevel, e); 363 if (transienterror(ret)) 364 { 365 if (LogLevel > 2) 366 sm_syslog(LOG_ERR, e->e_id, 367 "include %s: transient error: %s", 368 shortenstring(a->q_user, MAXSHORTSTR), 369 errstring(ret)); 370 a->q_flags |= QQUEUEUP; 371 a->q_flags &= ~QDONTSEND; 372 usrerr("451 Cannot open %s: %s", 373 shortenstring(a->q_user, MAXSHORTSTR), 374 errstring(ret)); 375 } 376 else if (ret != 0) 377 { 378 a->q_flags |= QBADADDR; 379 a->q_status = "5.2.4"; 380 usrerr("550 Cannot open %s: %s", 381 shortenstring(a->q_user, MAXSHORTSTR), 382 errstring(ret)); 383 } 384 } 385 } 386 else if (m == FileMailer) 387 { 388 extern bool writable __P((char *, ADDRESS *, int)); 389 390 /* check if writable or creatable */ 391 if (a->q_alias == NULL) 392 { 393 a->q_flags |= QBADADDR; 394 a->q_status = "5.7.1"; 395 usrerr("550 Cannot mail directly to files"); 396 } 397 else if (bitset(QBOGUSSHELL, a->q_alias->q_flags)) 398 { 399 a->q_flags |= QBADADDR; 400 a->q_status = "5.7.1"; 401 if (a->q_alias->q_ruser == NULL) 402 usrerr("550 UID %d is an unknown user: cannot mail to files", 403 a->q_alias->q_uid); 404 else 405 usrerr("550 User %s@%s doesn't have a valid shell for mailing to files", 406 a->q_alias->q_ruser, MyHostName); 407 } 408 else if (bitset(QUNSAFEADDR, a->q_alias->q_flags)) 409 { 410 a->q_flags |= QBADADDR; 411 a->q_status = "5.7.1"; 412 a->q_rstatus = newstr("Unsafe for mailing to files"); 413 usrerr("550 Address %s is unsafe for mailing to files", 414 a->q_alias->q_paddr); 415 } 416 else if (strcmp(buf, "/dev/null") == 0) 417 { 418 /* /dev/null is always accepted */ 419 } 420 else if (!writable(buf, a->q_alias, SFF_CREAT)) 421 { 422 a->q_flags |= QBADADDR; 423 giveresponse(EX_CANTCREAT, m, NULL, a->q_alias, 424 (time_t) 0, e); 425 } 426 } 427 428 /* try aliasing */ 429 if (!quoted && !bitset(QDONTSEND, a->q_flags) && 430 bitnset(M_ALIASABLE, m->m_flags)) 431 alias(a, sendq, aliaslevel, e); 432 433# if USERDB 434 /* if not aliased, look it up in the user database */ 435 if (!bitset(QDONTSEND|QNOTREMOTE|QVERIFIED, a->q_flags) && 436 bitnset(M_CHECKUDB, m->m_flags)) 437 { 438 extern int udbexpand __P((ADDRESS *, ADDRESS **, int, ENVELOPE *)); 439 440 if (udbexpand(a, sendq, aliaslevel, e) == EX_TEMPFAIL) 441 { 442 a->q_flags |= QQUEUEUP; 443 if (e->e_message == NULL) 444 e->e_message = newstr("Deferred: user database error"); 445 if (LogLevel > 8) 446 sm_syslog(LOG_INFO, e->e_id, 447 "deferred: udbexpand: %s", 448 errstring(errno)); 449 message("queued (user database error): %s", 450 errstring(errno)); 451 e->e_nrcpts++; 452 goto testselfdestruct; 453 } 454 } 455# endif 456 457 /* 458 ** If we have a level two config file, then pass the name through 459 ** Ruleset 5 before sending it off. Ruleset 5 has the right 460 ** to send rewrite it to another mailer. This gives us a hook 461 ** after local aliasing has been done. 462 */ 463 464 if (tTd(29, 5)) 465 { 466 printf("recipient: testing local? cl=%d, rr5=%lx\n\t", 467 ConfigLevel, (u_long) RewriteRules[5]); 468 printaddr(a, FALSE); 469 } 470 if (!bitset(QNOTREMOTE|QDONTSEND|QQUEUEUP|QVERIFIED, a->q_flags) && 471 ConfigLevel >= 2 && RewriteRules[5] != NULL && 472 bitnset(M_TRYRULESET5, m->m_flags)) 473 { 474 extern void maplocaluser __P((ADDRESS *, ADDRESS **, int, ENVELOPE *)); 475 476 maplocaluser(a, sendq, aliaslevel + 1, e); 477 } 478 479 /* 480 ** If it didn't get rewritten to another mailer, go ahead 481 ** and deliver it. 482 */ 483 484 if (!bitset(QDONTSEND|QQUEUEUP|QVERIFIED, a->q_flags) && 485 bitnset(M_HASPWENT, m->m_flags)) 486 { 487 auto bool fuzzy; 488 register struct passwd *pw; 489 extern void forward __P((ADDRESS *, ADDRESS **, int, ENVELOPE *)); 490 491 /* warning -- finduser may trash buf */ 492 pw = finduser(buf, &fuzzy); 493 if (pw == NULL || strlen(pw->pw_name) > MAXNAME) 494 { 495 a->q_flags |= QBADADDR; 496 a->q_status = "5.1.1"; 497 giveresponse(EX_NOUSER, m, NULL, a->q_alias, 498 (time_t) 0, e); 499 } 500 else 501 { 502 char nbuf[MAXNAME + 1]; 503 504 if (fuzzy) 505 { 506 /* name was a fuzzy match */ 507 a->q_user = newstr(pw->pw_name); 508 if (findusercount++ > 3) 509 { 510 a->q_flags |= QBADADDR; 511 a->q_status = "5.4.6"; 512 usrerr("554 aliasing/forwarding loop for %s broken", 513 pw->pw_name); 514 goto done; 515 } 516 517 /* see if it aliases */ 518 (void) strcpy(buf, pw->pw_name); 519 goto trylocaluser; 520 } 521 if (strcmp(pw->pw_dir, "/") == 0) 522 a->q_home = ""; 523 else 524 a->q_home = newstr(pw->pw_dir); 525 a->q_uid = pw->pw_uid; 526 a->q_gid = pw->pw_gid; 527 a->q_ruser = newstr(pw->pw_name); 528 a->q_flags |= QGOODUID; 529 buildfname(pw->pw_gecos, pw->pw_name, nbuf, sizeof nbuf); 530 if (nbuf[0] != '\0') 531 a->q_fullname = newstr(nbuf); 532 if (!usershellok(pw->pw_name, pw->pw_shell)) 533 { 534 a->q_flags |= QBOGUSSHELL; 535 } 536 if (bitset(EF_VRFYONLY, e->e_flags)) 537 { 538 /* don't do any more now */ 539 a->q_flags |= QVERIFIED; 540 } 541 else if (!quoted) 542 forward(a, sendq, aliaslevel, e); 543 } 544 } 545 if (!bitset(QDONTSEND, a->q_flags)) 546 e->e_nrcpts++; 547 548 testselfdestruct: 549 a->q_flags |= QTHISPASS; 550 if (tTd(26, 8)) 551 { 552 printf("testselfdestruct: "); 553 printaddr(a, FALSE); 554 if (tTd(26, 10)) 555 { 556 printf("SENDQ:\n"); 557 printaddr(*sendq, TRUE); 558 printf("----\n"); 559 } 560 } 561 if (a->q_alias == NULL && a != &e->e_from && 562 bitset(QDONTSEND, a->q_flags)) 563 { 564 for (q = *sendq; q != NULL; q = q->q_next) 565 { 566 if (!bitset(QDONTSEND, q->q_flags)) 567 break; 568 } 569 if (q == NULL) 570 { 571 a->q_flags |= QBADADDR; 572 a->q_status = "5.4.6"; 573 usrerr("554 aliasing/forwarding loop broken"); 574 } 575 } 576 577 done: 578 a->q_flags |= QTHISPASS; 579 if (buf != buf0) 580 free(buf); 581 582 /* 583 ** If we are at the top level, check to see if this has 584 ** expanded to exactly one address. If so, it can inherit 585 ** the primaryness of the address. 586 ** 587 ** While we're at it, clear the QTHISPASS bits. 588 */ 589 590 if (aliaslevel == 0) 591 { 592 int nrcpts = 0; 593 ADDRESS *only = NULL; 594 595 for (q = *sendq; q != NULL; q = q->q_next) 596 { 597 if (bitset(QTHISPASS, q->q_flags) && 598 !bitset(QDONTSEND|QBADADDR, q->q_flags)) 599 { 600 nrcpts++; 601 only = q; 602 } 603 q->q_flags &= ~QTHISPASS; 604 } 605 if (nrcpts == 1) 606 { 607 /* check to see if this actually got a new owner */ 608 q = only; 609 while ((q = q->q_alias) != NULL) 610 { 611 if (q->q_owner != NULL) 612 break; 613 } 614 if (q == NULL) 615 only->q_flags |= QPRIMARY; 616 } 617 else if (!initialdontsend && nrcpts > 0) 618 { 619 /* arrange for return receipt */ 620 e->e_flags |= EF_SENDRECEIPT; 621 a->q_flags |= QEXPANDED; 622 if (e->e_xfp != NULL && bitset(QPINGONSUCCESS, a->q_flags)) 623 fprintf(e->e_xfp, 624 "%s... expanded to multiple addresses\n", 625 a->q_paddr); 626 } 627 } 628 a->q_flags |= QRCPTOK; 629 return (a); 630} 631/* 632** FINDUSER -- find the password entry for a user. 633** 634** This looks a lot like getpwnam, except that it may want to 635** do some fancier pattern matching in /etc/passwd. 636** 637** This routine contains most of the time of many sendmail runs. 638** It deserves to be optimized. 639** 640** Parameters: 641** name -- the name to match against. 642** fuzzyp -- an outarg that is set to TRUE if this entry 643** was found using the fuzzy matching algorithm; 644** set to FALSE otherwise. 645** 646** Returns: 647** A pointer to a pw struct. 648** NULL if name is unknown or ambiguous. 649** 650** Side Effects: 651** may modify name. 652*/ 653 654struct passwd * 655finduser(name, fuzzyp) 656 char *name; 657 bool *fuzzyp; 658{ 659 register struct passwd *pw; 660 register char *p; 661 bool tryagain; 662 663 if (tTd(29, 4)) 664 printf("finduser(%s): ", name); 665 666 *fuzzyp = FALSE; 667 668#ifdef HESIOD 669 /* DEC Hesiod getpwnam accepts numeric strings -- short circuit it */ 670 for (p = name; *p != '\0'; p++) 671 if (!isascii(*p) || !isdigit(*p)) 672 break; 673 if (*p == '\0') 674 { 675 if (tTd(29, 4)) 676 printf("failed (numeric input)\n"); 677 return NULL; 678 } 679#endif 680 681 /* look up this login name using fast path */ 682 if ((pw = sm_getpwnam(name)) != NULL) 683 { 684 if (tTd(29, 4)) 685 printf("found (non-fuzzy)\n"); 686 return (pw); 687 } 688 689 /* try mapping it to lower case */ 690 tryagain = FALSE; 691 for (p = name; *p != '\0'; p++) 692 { 693 if (isascii(*p) && isupper(*p)) 694 { 695 *p = tolower(*p); 696 tryagain = TRUE; 697 } 698 } 699 if (tryagain && (pw = sm_getpwnam(name)) != NULL) 700 { 701 if (tTd(29, 4)) 702 printf("found (lower case)\n"); 703 *fuzzyp = TRUE; 704 return pw; 705 } 706 707#if MATCHGECOS 708 /* see if fuzzy matching allowed */ 709 if (!MatchGecos) 710 { 711 if (tTd(29, 4)) 712 printf("not found (fuzzy disabled)\n"); 713 return NULL; 714 } 715 716 /* search for a matching full name instead */ 717 for (p = name; *p != '\0'; p++) 718 { 719 if (*p == (SpaceSub & 0177) || *p == '_') 720 *p = ' '; 721 } 722 (void) setpwent(); 723 while ((pw = getpwent()) != NULL) 724 { 725 char buf[MAXNAME + 1]; 726 727# if 0 728 if (strcasecmp(pw->pw_name, name) == 0) 729 { 730 if (tTd(29, 4)) 731 printf("found (case wrapped)\n"); 732 break; 733 } 734# endif 735 736 buildfname(pw->pw_gecos, pw->pw_name, buf, sizeof buf); 737 if (strchr(buf, ' ') != NULL && !strcasecmp(buf, name)) 738 { 739 if (tTd(29, 4)) 740 printf("fuzzy matches %s\n", pw->pw_name); 741 message("sending to login name %s", pw->pw_name); 742 break; 743 } 744 } 745 if (pw != NULL) 746 *fuzzyp = TRUE; 747 else if (tTd(29, 4)) 748 printf("no fuzzy match found\n"); 749# if DEC_OSF_BROKEN_GETPWENT /* DEC OSF/1 3.2 or earlier */ 750 endpwent(); 751# endif 752 return pw; 753#else 754 if (tTd(29, 4)) 755 printf("not found (fuzzy disabled)\n"); 756 return NULL; 757#endif 758} 759/* 760** WRITABLE -- predicate returning if the file is writable. 761** 762** This routine must duplicate the algorithm in sys/fio.c. 763** Unfortunately, we cannot use the access call since we 764** won't necessarily be the real uid when we try to 765** actually open the file. 766** 767** Notice that ANY file with ANY execute bit is automatically 768** not writable. This is also enforced by mailfile. 769** 770** Parameters: 771** filename -- the file name to check. 772** ctladdr -- the controlling address for this file. 773** flags -- SFF_* flags to control the function. 774** 775** Returns: 776** TRUE -- if we will be able to write this file. 777** FALSE -- if we cannot write this file. 778** 779** Side Effects: 780** none. 781*/ 782 783bool 784writable(filename, ctladdr, flags) 785 char *filename; 786 ADDRESS *ctladdr; 787 int flags; 788{ 789 uid_t euid; 790 gid_t egid; 791 char *uname; 792 793 if (tTd(44, 5)) 794 printf("writable(%s, 0x%x)\n", filename, flags); 795 796 /* 797 ** File does exist -- check that it is writable. 798 */ 799 800 if (geteuid() != 0) 801 { 802 euid = geteuid(); 803 egid = getegid(); 804 uname = NULL; 805 } 806 else if (ctladdr != NULL) 807 { 808 euid = ctladdr->q_uid; 809 egid = ctladdr->q_gid; 810 uname = ctladdr->q_user; 811 } 812 else if (bitset(SFF_RUNASREALUID, flags)) 813 { 814 euid = RealUid; 815 egid = RealGid; 816 uname = RealUserName; 817 } 818 else if (FileMailer != NULL && !bitset(SFF_ROOTOK, flags)) 819 { 820 euid = FileMailer->m_uid; 821 egid = FileMailer->m_gid; 822 uname = NULL; 823 } 824 else 825 { 826 euid = egid = 0; 827 uname = NULL; 828 } 829 if (!bitset(SFF_ROOTOK, flags)) 830 { 831 if (euid == 0) 832 { 833 euid = DefUid; 834 uname = DefUser; 835 } 836 if (egid == 0) 837 egid = DefGid; 838 } 839 if (geteuid() == 0 && 840 (ctladdr == NULL || !bitset(QGOODUID, ctladdr->q_flags))) 841 flags |= SFF_SETUIDOK; 842 843 if (!bitset(DBS_FILEDELIVERYTOSYMLINK, DontBlameSendmail)) 844 flags |= SFF_NOSLINK; 845 if (!bitset(DBS_FILEDELIVERYTOHARDLINK, DontBlameSendmail)) 846 flags |= SFF_NOHLINK; 847 848 errno = safefile(filename, euid, egid, uname, flags, S_IWRITE, NULL); 849 return errno == 0; 850} 851/* 852** INCLUDE -- handle :include: specification. 853** 854** Parameters: 855** fname -- filename to include. 856** forwarding -- if TRUE, we are reading a .forward file. 857** if FALSE, it's a :include: file. 858** ctladdr -- address template to use to fill in these 859** addresses -- effective user/group id are 860** the important things. 861** sendq -- a pointer to the head of the send queue 862** to put these addresses in. 863** aliaslevel -- the alias nesting depth. 864** e -- the current envelope. 865** 866** Returns: 867** open error status 868** 869** Side Effects: 870** reads the :include: file and sends to everyone 871** listed in that file. 872** 873** Security Note: 874** If you have restricted chown (that is, you can't 875** give a file away), it is reasonable to allow programs 876** and files called from this :include: file to be to be 877** run as the owner of the :include: file. This is bogus 878** if there is any chance of someone giving away a file. 879** We assume that pre-POSIX systems can give away files. 880** 881** There is an additional restriction that if you 882** forward to a :include: file, it will not take on 883** the ownership of the :include: file. This may not 884** be necessary, but shouldn't hurt. 885*/ 886 887static jmp_buf CtxIncludeTimeout; 888static void includetimeout __P((void)); 889 890int 891include(fname, forwarding, ctladdr, sendq, aliaslevel, e) 892 char *fname; 893 bool forwarding; 894 ADDRESS *ctladdr; 895 ADDRESS **sendq; 896 int aliaslevel; 897 ENVELOPE *e; 898{ 899 FILE *volatile fp = NULL; 900 char *oldto = e->e_to; 901 char *oldfilename = FileName; 902 int oldlinenumber = LineNumber; 903 register EVENT *ev = NULL; 904 int nincludes; 905 int mode; 906 register ADDRESS *ca; 907 volatile uid_t saveduid, uid; 908 volatile gid_t savedgid, gid; 909 char *volatile uname; 910 int rval = 0; 911 volatile int sfflags = SFF_REGONLY; 912 register char *p; 913 bool safechown = FALSE; 914 volatile bool safedir = FALSE; 915 struct stat st; 916 char buf[MAXLINE]; 917 extern bool chownsafe __P((int, bool)); 918 919 if (tTd(27, 2)) 920 printf("include(%s)\n", fname); 921 if (tTd(27, 4)) 922 printf(" ruid=%d euid=%d\n", (int) getuid(), (int) geteuid()); 923 if (tTd(27, 14)) 924 { 925 printf("ctladdr "); 926 printaddr(ctladdr, FALSE); 927 } 928 929 if (tTd(27, 9)) 930 printf("include: old uid = %d/%d\n", 931 (int) getuid(), (int) geteuid()); 932 933 if (forwarding) 934 sfflags |= SFF_MUSTOWN|SFF_ROOTOK|SFF_NOSLINK; 935 936 ca = getctladdr(ctladdr); 937 if (ca == NULL) 938 { 939 uid = DefUid; 940 gid = DefGid; 941 uname = DefUser; 942 } 943 else 944 { 945 uid = ca->q_uid; 946 gid = ca->q_gid; 947 uname = ca->q_user; 948 } 949#if HASSETREUID || USESETEUID 950 saveduid = geteuid(); 951 savedgid = getegid(); 952 if (saveduid == 0) 953 { 954 if (!DontInitGroups) 955 { 956 if (initgroups(uname, gid) == -1) 957 syserr("include: initgroups(%s, %d) failed", 958 uname, gid); 959 } 960 else 961 { 962 GIDSET_T gidset[1]; 963 964 gidset[0] = gid; 965 if (setgroups(1, gidset) == -1) 966 syserr("include: setgroups() failed"); 967 } 968 969 if (gid != 0 && setgid(gid) < -1) 970 syserr("setgid(%d) failure", gid); 971 if (uid != 0) 972 { 973# if USESETEUID 974 if (seteuid(uid) < 0) 975 syserr("seteuid(%d) failure (real=%d, eff=%d)", 976 uid, getuid(), geteuid()); 977# else 978 if (setreuid(0, uid) < 0) 979 syserr("setreuid(0, %d) failure (real=%d, eff=%d)", 980 uid, getuid(), geteuid()); 981# endif 982 } 983 } 984#endif 985 986 if (tTd(27, 9)) 987 printf("include: new uid = %d/%d\n", 988 (int) getuid(), (int) geteuid()); 989 990 /* 991 ** If home directory is remote mounted but server is down, 992 ** this can hang or give errors; use a timeout to avoid this 993 */ 994 995 if (setjmp(CtxIncludeTimeout) != 0) 996 { 997 ctladdr->q_flags |= QQUEUEUP; 998 errno = 0; 999 1000 /* return pseudo-error code */ 1001 rval = E_SM_OPENTIMEOUT; 1002 goto resetuid; 1003 } 1004 if (TimeOuts.to_fileopen > 0) 1005 ev = setevent(TimeOuts.to_fileopen, includetimeout, 0); 1006 else 1007 ev = NULL; 1008 1009 /* check for writable parent directory */ 1010 p = strrchr(fname, '/'); 1011 if (p != NULL) 1012 { 1013 int ret; 1014 1015 *p = '\0'; 1016 ret = safedirpath(fname, uid, gid, uname, sfflags|SFF_SAFEDIRPATH); 1017 if (ret == 0) 1018 { 1019 /* in safe directory: relax chown & link rules */ 1020 safedir = TRUE; 1021 sfflags |= SFF_NOPATHCHECK; 1022 } 1023 else 1024 { 1025 if (bitset((forwarding ? 1026 DBS_FORWARDFILEINUNSAFEDIRPATH : 1027 DBS_INCLUDEFILEINUNSAFEDIRPATH), 1028 DontBlameSendmail)) 1029 sfflags |= SFF_NOPATHCHECK; 1030 else if (bitset((forwarding ? 1031 DBS_FORWARDFILEINGROUPWRITABLEDIRPATH : 1032 DBS_INCLUDEFILEINGROUPWRITABLEDIRPATH), 1033 DontBlameSendmail) && 1034 ret == E_SM_GWDIR) 1035 { 1036 DontBlameSendmail |= DBS_GROUPWRITABLEDIRPATHSAFE; 1037 ret = safedirpath(fname, uid, 1038 gid, uname, 1039 sfflags|SFF_SAFEDIRPATH); 1040 DontBlameSendmail &= ~DBS_GROUPWRITABLEDIRPATHSAFE; 1041 if (ret == 0) 1042 sfflags |= SFF_NOPATHCHECK; 1043 else 1044 sfflags |= SFF_SAFEDIRPATH; 1045 } 1046 else 1047 sfflags |= SFF_SAFEDIRPATH; 1048 if (ret > E_PSEUDOBASE && 1049 !bitset((forwarding ? 1050 DBS_FORWARDFILEINUNSAFEDIRPATHSAFE : 1051 DBS_INCLUDEFILEINUNSAFEDIRPATHSAFE), 1052 DontBlameSendmail)) 1053 { 1054 if (LogLevel >= 12) 1055 sm_syslog(LOG_INFO, e->e_id, 1056 "%s: unsafe directory path, marked unsafe", 1057 shortenstring(fname, MAXSHORTSTR)); 1058 ctladdr->q_flags |= QUNSAFEADDR; 1059 } 1060 } 1061 *p = '/'; 1062 } 1063 1064 /* allow links only in unwritable directories */ 1065 if (!safedir && 1066 !bitset((forwarding ? 1067 DBS_LINKEDFORWARDFILEINWRITABLEDIR : 1068 DBS_LINKEDINCLUDEFILEINWRITABLEDIR), 1069 DontBlameSendmail)) 1070 sfflags |= SFF_NOLINK; 1071 1072 rval = safefile(fname, uid, gid, uname, sfflags, S_IREAD, &st); 1073 if (rval != 0) 1074 { 1075 /* don't use this :include: file */ 1076 if (tTd(27, 4)) 1077 printf("include: not safe (uid=%d): %s\n", 1078 (int) uid, errstring(rval)); 1079 } 1080 else if ((fp = fopen(fname, "r")) == NULL) 1081 { 1082 rval = errno; 1083 if (tTd(27, 4)) 1084 printf("include: open: %s\n", errstring(rval)); 1085 } 1086 else if (filechanged(fname, fileno(fp), &st)) 1087 { 1088 rval = E_SM_FILECHANGE; 1089 if (tTd(27, 4)) 1090 printf("include: file changed after open\n"); 1091 } 1092 if (ev != NULL) 1093 clrevent(ev); 1094 1095resetuid: 1096 1097#if HASSETREUID || USESETEUID 1098 if (saveduid == 0) 1099 { 1100 if (uid != 0) 1101 { 1102# if USESETEUID 1103 if (seteuid(0) < 0) 1104 syserr("seteuid(0) failure (real=%d, eff=%d)", 1105 getuid(), geteuid()); 1106# else 1107 if (setreuid(-1, 0) < 0) 1108 syserr("setreuid(-1, 0) failure (real=%d, eff=%d)", 1109 getuid(), geteuid()); 1110 if (setreuid(RealUid, 0) < 0) 1111 syserr("setreuid(%d, 0) failure (real=%d, eff=%d)", 1112 RealUid, getuid(), geteuid()); 1113# endif 1114 } 1115 setgid(savedgid); 1116 } 1117#endif 1118 1119 if (tTd(27, 9)) 1120 printf("include: reset uid = %d/%d\n", 1121 (int) getuid(), (int) geteuid()); 1122 1123 if (rval == E_SM_OPENTIMEOUT) 1124 usrerr("451 open timeout on %s", fname); 1125 1126 if (fp == NULL) 1127 return rval; 1128 1129 if (fstat(fileno(fp), &st) < 0) 1130 { 1131 rval = errno; 1132 syserr("Cannot fstat %s!", fname); 1133 return rval; 1134 } 1135 1136 /* if path was writable, check to avoid file giveaway tricks */ 1137 safechown = chownsafe(fileno(fp), safedir); 1138 if (tTd(27, 6)) 1139 printf("include: parent of %s is %s, chown is %ssafe\n", 1140 fname, 1141 safedir ? "safe" : "dangerous", 1142 safechown ? "" : "un"); 1143 1144 if (ca == NULL && safechown) 1145 { 1146 ctladdr->q_uid = st.st_uid; 1147 ctladdr->q_gid = st.st_gid; 1148 ctladdr->q_flags |= QGOODUID; 1149 } 1150 if (ca != NULL && ca->q_uid == st.st_uid) 1151 { 1152 /* optimization -- avoid getpwuid if we already have info */ 1153 ctladdr->q_flags |= ca->q_flags & QBOGUSSHELL; 1154 ctladdr->q_ruser = ca->q_ruser; 1155 } 1156 else if (!forwarding) 1157 { 1158 register struct passwd *pw; 1159 1160 pw = sm_getpwuid(st.st_uid); 1161 if (pw == NULL) 1162 ctladdr->q_flags |= QBOGUSSHELL; 1163 else 1164 { 1165 char *sh; 1166 1167 ctladdr->q_ruser = newstr(pw->pw_name); 1168 if (safechown) 1169 sh = pw->pw_shell; 1170 else 1171 sh = "/SENDMAIL/ANY/SHELL/"; 1172 if (!usershellok(pw->pw_name, sh)) 1173 { 1174 if (LogLevel >= 12) 1175 sm_syslog(LOG_INFO, e->e_id, 1176 "%s: user %s has bad shell %s, marked %s", 1177 shortenstring(fname, MAXSHORTSTR), 1178 pw->pw_name, sh, 1179 safechown ? "bogus" : "unsafe"); 1180 if (safechown) 1181 ctladdr->q_flags |= QBOGUSSHELL; 1182 else 1183 ctladdr->q_flags |= QUNSAFEADDR; 1184 } 1185 } 1186 } 1187 1188 if (bitset(EF_VRFYONLY, e->e_flags)) 1189 { 1190 /* don't do any more now */ 1191 ctladdr->q_flags |= QVERIFIED; 1192 e->e_nrcpts++; 1193 xfclose(fp, "include", fname); 1194 return rval; 1195 } 1196 1197 /* 1198 ** Check to see if some bad guy can write this file 1199 ** 1200 ** Group write checking could be more clever, e.g., 1201 ** guessing as to which groups are actually safe ("sys" 1202 ** may be; "user" probably is not). 1203 */ 1204 1205 mode = S_IWOTH; 1206 if (!bitset((forwarding ? 1207 DBS_GROUPWRITABLEFORWARDFILESAFE : 1208 DBS_GROUPWRITABLEINCLUDEFILESAFE), 1209 DontBlameSendmail)) 1210 mode |= S_IWGRP; 1211 1212 if (bitset(mode, st.st_mode)) 1213 { 1214 if (tTd(27, 6)) 1215 printf("include: %s is %s writable, marked unsafe\n", 1216 shortenstring(fname, MAXSHORTSTR), 1217 bitset(S_IWOTH, st.st_mode) ? "world" : "group"); 1218 if (LogLevel >= 12) 1219 sm_syslog(LOG_INFO, e->e_id, 1220 "%s: %s writable %s file, marked unsafe", 1221 shortenstring(fname, MAXSHORTSTR), 1222 bitset(S_IWOTH, st.st_mode) ? "world" : "group", 1223 forwarding ? "forward" : ":include:"); 1224 ctladdr->q_flags |= QUNSAFEADDR; 1225 } 1226 1227 /* read the file -- each line is a comma-separated list. */ 1228 FileName = fname; 1229 LineNumber = 0; 1230 ctladdr->q_flags &= ~QSELFREF; 1231 nincludes = 0; 1232 while (fgets(buf, sizeof buf, fp) != NULL) 1233 { 1234 register char *p = strchr(buf, '\n'); 1235 1236 LineNumber++; 1237 if (p != NULL) 1238 *p = '\0'; 1239 if (buf[0] == '#' || buf[0] == '\0') 1240 continue; 1241 1242 /* <sp>#@# introduces a comment anywhere */ 1243 /* for Japanese character sets */ 1244 for (p = buf; (p = strchr(++p, '#')) != NULL; ) 1245 { 1246 if (p[1] == '@' && p[2] == '#' && 1247 isascii(p[-1]) && isspace(p[-1]) && 1248 (p[3] == '\0' || (isascii(p[3]) && isspace(p[3])))) 1249 { 1250 p[-1] = '\0'; 1251 break; 1252 } 1253 } 1254 if (buf[0] == '\0') 1255 continue; 1256 1257 e->e_to = NULL; 1258 message("%s to %s", 1259 forwarding ? "forwarding" : "sending", buf); 1260 if (forwarding && LogLevel > 9) 1261 sm_syslog(LOG_INFO, e->e_id, 1262 "forward %.200s => %s", 1263 oldto, shortenstring(buf, MAXSHORTSTR)); 1264 1265 nincludes += sendtolist(buf, ctladdr, sendq, aliaslevel + 1, e); 1266 } 1267 1268 if (ferror(fp) && tTd(27, 3)) 1269 printf("include: read error: %s\n", errstring(errno)); 1270 if (nincludes > 0 && !bitset(QSELFREF, ctladdr->q_flags)) 1271 { 1272 if (tTd(27, 5)) 1273 { 1274 printf("include: QDONTSEND "); 1275 printaddr(ctladdr, FALSE); 1276 } 1277 ctladdr->q_flags |= QDONTSEND; 1278 } 1279 1280 (void) xfclose(fp, "include", fname); 1281 FileName = oldfilename; 1282 LineNumber = oldlinenumber; 1283 e->e_to = oldto; 1284 return rval; 1285} 1286 1287static void 1288includetimeout() 1289{ 1290 longjmp(CtxIncludeTimeout, 1); 1291} 1292/* 1293** SENDTOARGV -- send to an argument vector. 1294** 1295** Parameters: 1296** argv -- argument vector to send to. 1297** e -- the current envelope. 1298** 1299** Returns: 1300** none. 1301** 1302** Side Effects: 1303** puts all addresses on the argument vector onto the 1304** send queue. 1305*/ 1306 1307void 1308sendtoargv(argv, e) 1309 register char **argv; 1310 register ENVELOPE *e; 1311{ 1312 register char *p; 1313 1314 while ((p = *argv++) != NULL) 1315 { 1316 (void) sendtolist(p, NULLADDR, &e->e_sendqueue, 0, e); 1317 } 1318} 1319/* 1320** GETCTLADDR -- get controlling address from an address header. 1321** 1322** If none, get one corresponding to the effective userid. 1323** 1324** Parameters: 1325** a -- the address to find the controller of. 1326** 1327** Returns: 1328** the controlling address. 1329** 1330** Side Effects: 1331** none. 1332*/ 1333 1334ADDRESS * 1335getctladdr(a) 1336 register ADDRESS *a; 1337{ 1338 while (a != NULL && !bitset(QGOODUID, a->q_flags)) 1339 a = a->q_alias; 1340 return (a); 1341} 1342/* 1343** SELF_REFERENCE -- check to see if an address references itself 1344** 1345** The check is done through a chain of aliases. If it is part of 1346** a loop, break the loop at the "best" address, that is, the one 1347** that exists as a real user. 1348** 1349** This is to handle the case of: 1350** awc: Andrew.Chang 1351** Andrew.Chang: awc@mail.server 1352** which is a problem only on mail.server. 1353** 1354** Parameters: 1355** a -- the address to check. 1356** e -- the current envelope. 1357** 1358** Returns: 1359** The address that should be retained. 1360*/ 1361 1362ADDRESS * 1363self_reference(a, e) 1364 ADDRESS *a; 1365 ENVELOPE *e; 1366{ 1367 ADDRESS *b; /* top entry in self ref loop */ 1368 ADDRESS *c; /* entry that point to a real mail box */ 1369 1370 if (tTd(27, 1)) 1371 printf("self_reference(%s)\n", a->q_paddr); 1372 1373 for (b = a->q_alias; b != NULL; b = b->q_alias) 1374 { 1375 if (sameaddr(a, b)) 1376 break; 1377 } 1378 1379 if (b == NULL) 1380 { 1381 if (tTd(27, 1)) 1382 printf("\t... no self ref\n"); 1383 return NULL; 1384 } 1385 1386 /* 1387 ** Pick the first address that resolved to a real mail box 1388 ** i.e has a pw entry. The returned value will be marked 1389 ** QSELFREF in recipient(), which in turn will disable alias() 1390 ** from marking it QDONTSEND, which mean it will be used 1391 ** as a deliverable address. 1392 ** 1393 ** The 2 key thing to note here are: 1394 ** 1) we are in a recursive call sequence: 1395 ** alias->sentolist->recipient->alias 1396 ** 2) normally, when we return back to alias(), the address 1397 ** will be marked QDONTSEND, since alias() assumes the 1398 ** expanded form will be used instead of the current address. 1399 ** This behaviour is turned off if the address is marked 1400 ** QSELFREF We set QSELFREF when we return to recipient(). 1401 */ 1402 1403 c = a; 1404 while (c != NULL) 1405 { 1406 if (bitnset(M_HASPWENT, c->q_mailer->m_flags)) 1407 { 1408 if (tTd(27, 2)) 1409 printf("\t... getpwnam(%s)... ", c->q_user); 1410 if (sm_getpwnam(c->q_user) != NULL) 1411 { 1412 if (tTd(27, 2)) 1413 printf("found\n"); 1414 1415 /* ought to cache results here */ 1416 if (sameaddr(b, c)) 1417 return b; 1418 else 1419 return c; 1420 } 1421 if (tTd(27, 2)) 1422 printf("failed\n"); 1423 } 1424 c = c->q_alias; 1425 } 1426 1427 if (tTd(27, 1)) 1428 printf("\t... cannot break loop for \"%s\"\n", a->q_paddr); 1429 1430 return NULL; 1431} 1432