11556Srgrimes/*- 21556Srgrimes * Copyright (c) 1992 Keith Muller. 31556Srgrimes * Copyright (c) 1992, 1993 41556Srgrimes * The Regents of the University of California. All rights reserved. 51556Srgrimes * 61556Srgrimes * This code is derived from software contributed to Berkeley by 71556Srgrimes * Keith Muller of the University of California, San Diego. 81556Srgrimes * 91556Srgrimes * Redistribution and use in source and binary forms, with or without 101556Srgrimes * modification, are permitted provided that the following conditions 111556Srgrimes * are met: 121556Srgrimes * 1. Redistributions of source code must retain the above copyright 131556Srgrimes * notice, this list of conditions and the following disclaimer. 141556Srgrimes * 2. Redistributions in binary form must reproduce the above copyright 151556Srgrimes * notice, this list of conditions and the following disclaimer in the 161556Srgrimes * documentation and/or other materials provided with the distribution. 171556Srgrimes * 4. Neither the name of the University nor the names of its contributors 181556Srgrimes * may be used to endorse or promote products derived from this software 191556Srgrimes * without specific prior written permission. 201556Srgrimes * 211556Srgrimes * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 221556Srgrimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 231556Srgrimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 241556Srgrimes * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 251556Srgrimes * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 261556Srgrimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 271556Srgrimes * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 281556Srgrimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 291556Srgrimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 301556Srgrimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 311556Srgrimes * SUCH DAMAGE. 321556Srgrimes */ 331556Srgrimes 341556Srgrimes#ifndef lint 3536049Scharnier#if 0 3636049Scharnierstatic char sccsid[] = "@(#)tty_subs.c 8.2 (Berkeley) 4/18/94"; 3736049Scharnier#endif 381556Srgrimes#endif /* not lint */ 3999110Sobrien#include <sys/cdefs.h> 4099110Sobrien__FBSDID("$FreeBSD$"); 411556Srgrimes 421556Srgrimes#include <sys/types.h> 431556Srgrimes#include <sys/stat.h> 441556Srgrimes#include <fcntl.h> 451556Srgrimes#include <stdio.h> 461556Srgrimes#include <unistd.h> 471556Srgrimes#include <stdlib.h> 481556Srgrimes#include <string.h> 491556Srgrimes#include "pax.h" 501556Srgrimes#include "extern.h" 511556Srgrimes#include <stdarg.h> 521556Srgrimes 531556Srgrimes/* 541556Srgrimes * routines that deal with I/O to and from the user 551556Srgrimes */ 561556Srgrimes 5776019Skris#define DEVTTY "/dev/tty" /* device for interactive i/o */ 581556Srgrimesstatic FILE *ttyoutf = NULL; /* output pointing at control tty */ 591556Srgrimesstatic FILE *ttyinf = NULL; /* input pointing at control tty */ 601556Srgrimes 611556Srgrimes/* 621556Srgrimes * tty_init() 6346684Skris * try to open the controlling terminal (if any) for this process. if the 641556Srgrimes * open fails, future ops that require user input will get an EOF 651556Srgrimes */ 661556Srgrimes 671556Srgrimesint 681556Srgrimestty_init(void) 691556Srgrimes{ 701556Srgrimes int ttyfd; 711556Srgrimes 7276019Skris if ((ttyfd = open(DEVTTY, O_RDWR)) >= 0) { 731556Srgrimes if ((ttyoutf = fdopen(ttyfd, "w")) != NULL) { 741556Srgrimes if ((ttyinf = fdopen(ttyfd, "r")) != NULL) 751556Srgrimes return(0); 761556Srgrimes (void)fclose(ttyoutf); 771556Srgrimes } 781556Srgrimes (void)close(ttyfd); 791556Srgrimes } 801556Srgrimes 811556Srgrimes if (iflag) { 8276017Skris paxwarn(1, "Fatal error, cannot open %s", DEVTTY); 831556Srgrimes return(-1); 841556Srgrimes } 851556Srgrimes return(0); 861556Srgrimes} 871556Srgrimes 881556Srgrimes/* 891556Srgrimes * tty_prnt() 901556Srgrimes * print a message using the specified format to the controlling tty 911556Srgrimes * if there is no controlling terminal, just return. 921556Srgrimes */ 931556Srgrimes 941556Srgrimesvoid 9575577Skristty_prnt(const char *fmt, ...) 961556Srgrimes{ 971556Srgrimes va_list ap; 981556Srgrimes if (ttyoutf == NULL) 991556Srgrimes return; 100104560Stjr va_start(ap, fmt); 1011556Srgrimes (void)vfprintf(ttyoutf, fmt, ap); 1021556Srgrimes va_end(ap); 1031556Srgrimes (void)fflush(ttyoutf); 1041556Srgrimes} 1051556Srgrimes 1061556Srgrimes/* 1071556Srgrimes * tty_read() 1081556Srgrimes * read a string from the controlling terminal if it is open into the 1091556Srgrimes * supplied buffer 1101556Srgrimes * Return: 1111556Srgrimes * 0 if data was read, -1 otherwise. 1121556Srgrimes */ 1131556Srgrimes 1141556Srgrimesint 1151556Srgrimestty_read(char *str, int len) 1161556Srgrimes{ 11790113Simp char *pt; 1181556Srgrimes 1191556Srgrimes if ((--len <= 0) || (ttyinf == NULL) || (fgets(str,len,ttyinf) == NULL)) 1201556Srgrimes return(-1); 1211556Srgrimes *(str + len) = '\0'; 1221556Srgrimes 1231556Srgrimes /* 1241556Srgrimes * strip off that trailing newline 1251556Srgrimes */ 1261556Srgrimes if ((pt = strchr(str, '\n')) != NULL) 1271556Srgrimes *pt = '\0'; 1281556Srgrimes return(0); 1291556Srgrimes} 1301556Srgrimes 1311556Srgrimes/* 13276017Skris * paxwarn() 13376017Skris * write a warning message to stderr. if "set" the exit value of pax 1341556Srgrimes * will be non-zero. 1351556Srgrimes */ 1361556Srgrimes 1371556Srgrimesvoid 13876017Skrispaxwarn(int set, const char *fmt, ...) 1391556Srgrimes{ 1401556Srgrimes va_list ap; 1411556Srgrimes va_start(ap, fmt); 1421556Srgrimes if (set) 1431556Srgrimes exit_val = 1; 1441556Srgrimes /* 1451556Srgrimes * when vflag we better ship out an extra \n to get this message on a 1461556Srgrimes * line by itself 1471556Srgrimes */ 1481556Srgrimes if (vflag && vfpart) { 14976351Skris (void)fflush(listf); 1501556Srgrimes (void)fputc('\n', stderr); 1511556Srgrimes vfpart = 0; 1521556Srgrimes } 1531556Srgrimes (void)fprintf(stderr, "%s: ", argv0); 1541556Srgrimes (void)vfprintf(stderr, fmt, ap); 1551556Srgrimes va_end(ap); 1561556Srgrimes (void)fputc('\n', stderr); 1571556Srgrimes} 1581556Srgrimes 1591556Srgrimes/* 16076017Skris * syswarn() 16176017Skris * write a warning message to stderr. if "set" the exit value of pax 1621556Srgrimes * will be non-zero. 1631556Srgrimes */ 1641556Srgrimes 1651556Srgrimesvoid 16676017Skrissyswarn(int set, int errnum, const char *fmt, ...) 1671556Srgrimes{ 1681556Srgrimes va_list ap; 1691556Srgrimes va_start(ap, fmt); 1701556Srgrimes if (set) 1711556Srgrimes exit_val = 1; 1721556Srgrimes /* 1731556Srgrimes * when vflag we better ship out an extra \n to get this message on a 1741556Srgrimes * line by itself 1751556Srgrimes */ 1761556Srgrimes if (vflag && vfpart) { 17776351Skris (void)fflush(listf); 1781556Srgrimes (void)fputc('\n', stderr); 1791556Srgrimes vfpart = 0; 1801556Srgrimes } 1811556Srgrimes (void)fprintf(stderr, "%s: ", argv0); 1821556Srgrimes (void)vfprintf(stderr, fmt, ap); 1831556Srgrimes va_end(ap); 1841556Srgrimes 1851556Srgrimes /* 1861556Srgrimes * format and print the errno 1871556Srgrimes */ 1881556Srgrimes if (errnum > 0) 18976017Skris (void)fprintf(stderr, " <%s>", strerror(errnum)); 1901556Srgrimes (void)fputc('\n', stderr); 1911556Srgrimes} 192