util.c revision 80818
133965Sjdp/*- 2130561Sobrien * Copyright (c) 1992, 1993 3218822Sdim * The Regents of the University of California. All rights reserved. 433965Sjdp * 577298Sobrien * Redistribution and use in source and binary forms, with or without 633965Sjdp * modification, are permitted provided that the following conditions 733965Sjdp * are met: 833965Sjdp * 1. Redistributions of source code must retain the above copyright 933965Sjdp * notice, this list of conditions and the following disclaimer. 1033965Sjdp * 2. Redistributions in binary form must reproduce the above copyright 1133965Sjdp * notice, this list of conditions and the following disclaimer in the 1233965Sjdp * documentation and/or other materials provided with the distribution. 1333965Sjdp * 3. All advertising materials mentioning features or use of this software 1433965Sjdp * must display the following acknowledgement: 1533965Sjdp * This product includes software developed by the University of 1633965Sjdp * California, Berkeley and its contributors. 1733965Sjdp * 4. Neither the name of the University nor the names of its contributors 1833965Sjdp * may be used to endorse or promote products derived from this software 1960484Sobrien * without specific prior written permission. 20218822Sdim * 21218822Sdim * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 2233965Sjdp * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 23218822Sdim * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 2433965Sjdp * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 2533965Sjdp * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 2689857Sobrien * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2733965Sjdp * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2833965Sjdp * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 2933965Sjdp * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 3033965Sjdp * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 3133965Sjdp * SUCH DAMAGE. 32107492Sobrien */ 3333965Sjdp 3433965Sjdp#ifndef lint 3533965Sjdp#if 0 3633965Sjdpstatic char sccsid[] = "@(#)util.c 8.2 (Berkeley) 4/2/94"; 3733965Sjdp#endif 3833965Sjdpstatic const char rcsid[] = 3933965Sjdp "$FreeBSD: head/bin/rcp/util.c 80818 2001-08-01 05:12:39Z obrien $"; 4060484Sobrien#endif /* not lint */ 4160484Sobrien 4260484Sobrien#include <sys/param.h> 43130561Sobrien#include <sys/stat.h> 4460484Sobrien#include <sys/wait.h> 4533965Sjdp 4633965Sjdp#include <ctype.h> 4733965Sjdp#include <err.h> 4833965Sjdp#include <errno.h> 4933965Sjdp#include <paths.h> 5033965Sjdp#include <signal.h> 5133965Sjdp#include <stdio.h> 52218822Sdim#include <stdlib.h> 5333965Sjdp#include <string.h> 5433965Sjdp#include <unistd.h> 5533965Sjdp 56130561Sobrien#include "extern.h" 57130561Sobrien 58130561Sobrienchar * 59130561Sobriencolon(cp) 60130561Sobrien char *cp; 6133965Sjdp{ 6233965Sjdp if (*cp == ':') /* Leading colon is part of file name. */ 6333965Sjdp return (0); 6433965Sjdp 6533965Sjdp for (; *cp; ++cp) { 66130561Sobrien if (*cp == ':') 6733965Sjdp return (cp); 6833965Sjdp if (*cp == '/') 6933965Sjdp return (0); 70130561Sobrien } 7133965Sjdp return (0); 72130561Sobrien} 7333965Sjdp 7433965Sjdpvoid 7533965Sjdpverifydir(cp) 7633965Sjdp char *cp; 7733965Sjdp{ 7833965Sjdp struct stat stb; 7933965Sjdp 8033965Sjdp if (!stat(cp, &stb)) { 8133965Sjdp if (S_ISDIR(stb.st_mode)) 8233965Sjdp return; 8333965Sjdp errno = ENOTDIR; 8477298Sobrien } 8577298Sobrien run_err("%s: %s", cp, strerror(errno)); 8633965Sjdp exit(1); 8733965Sjdp} 8833965Sjdp 8933965Sjdpint 9033965Sjdpokname(cp0) 9133965Sjdp char *cp0; 9233965Sjdp{ 9333965Sjdp int c; 9433965Sjdp char *cp; 9533965Sjdp 9633965Sjdp cp = cp0; 9733965Sjdp do { 9833965Sjdp c = *cp; 9933965Sjdp if (c & 0200) 10033965Sjdp goto bad; 10133965Sjdp if (!isalpha(c) && !isdigit(c) && c != '_' && c != '-' && c != '.') 10260484Sobrien goto bad; 10333965Sjdp } while (*++cp); 10433965Sjdp return (1); 10533965Sjdp 10633965Sjdpbad: warnx("%s: invalid user name", cp0); 10733965Sjdp return (0); 108130561Sobrien} 10933965Sjdp 11033965Sjdpint 11133965Sjdpsusystem(s, userid) 11233965Sjdp int userid; 11333965Sjdp char *s; 11433965Sjdp{ 11533965Sjdp sig_t istat, qstat; 11633965Sjdp int status; 11733965Sjdp pid_t pid; 11833965Sjdp 11933965Sjdp pid = vfork(); 12033965Sjdp switch (pid) { 12160484Sobrien case -1: 12260484Sobrien return (127); 12360484Sobrien 12460484Sobrien case 0: 125130561Sobrien (void)setuid(userid); 12660484Sobrien execl(_PATH_BSHELL, "sh", "-c", s, (char *)NULL); 12760484Sobrien _exit(127); 12860484Sobrien } 12960484Sobrien istat = signal(SIGINT, SIG_IGN); 13060484Sobrien qstat = signal(SIGQUIT, SIG_IGN); 13160484Sobrien if (waitpid(pid, &status, 0) < 0) 13260484Sobrien status = -1; 13360484Sobrien (void)signal(SIGINT, istat); 134218822Sdim (void)signal(SIGQUIT, qstat); 13560484Sobrien return (status); 13660484Sobrien} 13760484Sobrien 13860484SobrienBUF * 13960484Sobrienallocbuf(bp, fd, blksize) 14060484Sobrien BUF *bp; 14160484Sobrien int fd, blksize; 14260484Sobrien{ 14389857Sobrien struct stat stb; 14460484Sobrien size_t size; 14560484Sobrien 14660484Sobrien if (fstat(fd, &stb) < 0) { 14760484Sobrien run_err("fstat: %s", strerror(errno)); 14860484Sobrien return (0); 14960484Sobrien } 15060484Sobrien size = roundup(stb.st_blksize, blksize); 15160484Sobrien if (size == 0) 15260484Sobrien size = blksize; 153130561Sobrien if (bp->cnt >= size) 15460484Sobrien return (bp); 155130561Sobrien if ((bp->buf = realloc(bp->buf, size)) == NULL) { 156130561Sobrien bp->cnt = 0; 15760484Sobrien run_err("%s", strerror(errno)); 15860484Sobrien return (0); 15960484Sobrien } 16060484Sobrien bp->cnt = size; 16160484Sobrien return (bp); 16260484Sobrien} 16360484Sobrien 16460484Sobrienvoid 16560484Sobrienlostconn(signo) 16660484Sobrien int signo; 16760484Sobrien{ 16860484Sobrien if (!iamremote) 16960484Sobrien warnx("lost connection"); 17060484Sobrien exit(1); 17160484Sobrien} 17260484Sobrien