View | Details | Raw Unified | Return to bug 100921 | Differences between
and this patch

Collapse All | Expand All

(-)libexec/tftpd/tftpd.c (-19 / +43 lines)
Lines 109-115 static struct dirlist { Link Here
109
static int	suppress_naks;
109
static int	suppress_naks;
110
static int	logging;
110
static int	logging;
111
static int	ipchroot;
111
static int	ipchroot;
112
static int	create_new = 0;
112
static int	traditional_mode = 1;
113
static mode_t	mask = S_IWGRP|S_IWOTH;
113
static mode_t	mask = S_IWGRP|S_IWOTH;
114
114
115
static const char *errtomsg(int);
115
static const char *errtomsg(int);
Lines 158-164 main(int argc, char *argv[]) Link Here
158
			mask = strtol(optarg, NULL, 0);
158
			mask = strtol(optarg, NULL, 0);
159
			break;
159
			break;
160
		case 'w':
160
		case 'w':
161
			create_new = 1;
161
			traditional_mode = 0;
162
			break;
162
			break;
163
		default:
163
		default:
164
			syslog(LOG_WARNING, "ignoring unknown option -%c", ch);
164
			syslog(LOG_WARNING, "ignoring unknown option -%c", ch);
Lines 527-533 int Link Here
527
validate_access(char **filep, int mode)
527
validate_access(char **filep, int mode)
528
{
528
{
529
	struct stat stbuf;
529
	struct stat stbuf;
530
	int	fd;
530
	int	fd, crq;
531
	struct dirlist *dirp;
531
	struct dirlist *dirp;
532
	static char pathname[MAXPATHLEN];
532
	static char pathname[MAXPATHLEN];
533
	char *filename = *filep;
533
	char *filename = *filep;
Lines 554-569 validate_access(char **filep, int mode) Link Here
554
		/* If directory list is empty, allow access to any file */
554
		/* If directory list is empty, allow access to any file */
555
		if (dirp->name == NULL && dirp != dirs)
555
		if (dirp->name == NULL && dirp != dirs)
556
			return (EACCESS);
556
			return (EACCESS);
557
		if (stat(filename, &stbuf) < 0)
557
558
			return (errno == ENOENT ? ENOTFOUND : EACCESS);
558
		crq = 0;
559
		if ((stbuf.st_mode & S_IFMT) != S_IFREG)
559
		if (stat(filename, &stbuf) < 0) {
560
			return (ENOTFOUND);
560
			if (!traditional_mode && (mode == WRQ) && (errno == ENOENT))
561
		if (mode == RRQ) {
561
				crq = 1;
562
			if ((stbuf.st_mode & S_IROTH) == 0)
562
			if (!crq)
563
				return (EACCESS);
563
				return (errno == ENOENT ? ENOTFOUND : EACCESS);
564
		} else {
564
		}
565
			if ((stbuf.st_mode & S_IWOTH) == 0)
565
		if (!crq) {
566
				return (EACCESS);
566
			if ((stbuf.st_mode & S_IFMT) != S_IFREG)
567
				return (ENOTFOUND);
568
		}
569
		if (traditional_mode) {
570
			if (mode == RRQ) {
571
				if ((stbuf.st_mode & S_IROTH) == 0)
572
					return (EACCESS);
573
			} else {
574
				if ((stbuf.st_mode & S_IWOTH) == 0)
575
					return (EACCESS);
576
			}
567
		}
577
		}
568
	} else {
578
	} else {
569
		int err;
579
		int err;
Lines 588-603 validate_access(char **filep, int mode) Link Here
588
				dirp->name, filename);
598
				dirp->name, filename);
589
			if (stat(pathname, &stbuf) == 0 &&
599
			if (stat(pathname, &stbuf) == 0 &&
590
			    (stbuf.st_mode & S_IFMT) == S_IFREG) {
600
			    (stbuf.st_mode & S_IFMT) == S_IFREG) {
591
				if ((stbuf.st_mode & S_IROTH) != 0) {
601
				if (!traditional_mode)
592
					break;
602
					break;
603
				if (mode == RRQ) {
604
					if ((stbuf.st_mode & S_IROTH) != 0) {
605
						break;
606
					}
607
				} else {
608
					if ((stbuf.st_mode & S_IWOTH) != 0) {
609
						break;
610
					}
593
				}
611
				}
594
				err = EACCESS;
612
				err = EACCESS;
595
			}
613
			}
596
		}
614
		}
597
		if (dirp->name != NULL)
615
		if (dirp->name != NULL)
598
			*filep = filename = pathname;
616
			*filep = filename = pathname;
599
		else if (mode == RRQ)
617
		else {
600
			return (err);
618
			if (mode == RRQ) {
619
				return (err);
620
			} else {
621
				if (traditional_mode)
622
					return (err);
623
			}
624
		}
601
	}
625
	}
602
	if (options[OPT_TSIZE].o_request) {
626
	if (options[OPT_TSIZE].o_request) {
603
		if (mode == RRQ) 
627
		if (mode == RRQ) 
Lines 610-619 validate_access(char **filep, int mode) Link Here
610
	if (mode == RRQ)
634
	if (mode == RRQ)
611
		fd = open(filename, O_RDONLY);
635
		fd = open(filename, O_RDONLY);
612
	else {
636
	else {
613
		if (create_new)
637
		if (traditional_mode)
614
			fd = open(filename, O_WRONLY|O_TRUNC|O_CREAT, 0666);
615
		else
616
			fd = open(filename, O_WRONLY|O_TRUNC);
638
			fd = open(filename, O_WRONLY|O_TRUNC);
639
		else
640
			fd = open(filename, O_WRONLY|O_TRUNC|O_CREAT, 0666);
617
	}
641
	}
618
	if (fd < 0)
642
	if (fd < 0)
619
		return (errno + 100);
643
		return (errno + 100);

Return to bug 100921