kill.c revision 216629
1280849Scy/*- 2280849Scy * Copyright (c) 1988, 1993, 1994 3280849Scy * The Regents of the University of California. All rights reserved. 4280849Scy * 5280849Scy * Redistribution and use in source and binary forms, with or without 6280849Scy * modification, are permitted provided that the following conditions 7280849Scy * are met: 8280849Scy * 1. Redistributions of source code must retain the above copyright 9280849Scy * notice, this list of conditions and the following disclaimer. 10280849Scy * 2. Redistributions in binary form must reproduce the above copyright 11280849Scy * notice, this list of conditions and the following disclaimer in the 12280849Scy * documentation and/or other materials provided with the distribution. 13280849Scy * 4. Neither the name of the University nor the names of its contributors 14280849Scy * may be used to endorse or promote products derived from this software 15280849Scy * without specific prior written permission. 16280849Scy * 17280849Scy * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 18280849Scy * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 19280849Scy * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 20280849Scy * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 21280849Scy * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 22280849Scy * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 23275970Scy * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 24275970Scy * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 25275970Scy * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 26275970Scy * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 27275970Scy * SUCH DAMAGE. 28275970Scy */ 29275970Scy 30275970Scy#if 0 31275970Scy#ifndef lint 32275970Scystatic char const copyright[] = 33275970Scy"@(#) Copyright (c) 1988, 1993, 1994\n\ 34275970Scy The Regents of the University of California. All rights reserved.\n"; 35275970Scy#endif /* not lint */ 36275970Scy 37275970Scy#ifndef lint 38275970Scystatic char sccsid[] = "@(#)kill.c 8.4 (Berkeley) 4/28/95"; 39275970Scy#endif /* not lint */ 40275970Scy#endif 41275970Scy#include <sys/cdefs.h> 42275970Scy__FBSDID("$FreeBSD: head/bin/kill/kill.c 216629 2010-12-21 22:47:34Z jilles $"); 43275970Scy 44275970Scy#include <ctype.h> 45275970Scy#include <err.h> 46275970Scy#include <errno.h> 47275970Scy#include <signal.h> 48275970Scy#include <stdio.h> 49275970Scy#include <stdlib.h> 50275970Scy#include <string.h> 51275970Scy 52275970Scy#ifdef SHELL 53280849Scy#define main killcmd 54275970Scy#include "bltin/bltin.h" 55275970Scy#include "error.h" 56275970Scy#endif 57275970Scy 58275970Scystatic void nosig(const char *); 59275970Scystatic void printsignals(FILE *); 60275970Scystatic int signame_to_signum(const char *); 61275970Scystatic void usage(void); 62275970Scy 63275970Scyint 64275970Scymain(int argc, char *argv[]) 65275970Scy{ 66275970Scy int errors, numsig, pid; 67289997Sglebius char *ep; 68275970Scy 69275970Scy if (argc < 2) 70275970Scy usage(); 71275970Scy 72275970Scy numsig = SIGTERM; 73275970Scy 74275970Scy argc--, argv++; 75275970Scy if (!strcmp(*argv, "-l")) { 76275970Scy argc--, argv++; 77275970Scy if (argc > 1) 78275970Scy usage(); 79275970Scy if (argc == 1) { 80275970Scy if (!isdigit(**argv)) 81330567Sgordon usage(); 82330567Sgordon numsig = strtol(*argv, &ep, 10); 83330567Sgordon if (!**argv || *ep) 84330567Sgordon errx(2, "illegal signal number: %s", *argv); 85330567Sgordon if (numsig >= 128) 86330567Sgordon numsig -= 128; 87289997Sglebius if (numsig <= 0 || numsig >= sys_nsig) 88275970Scy nosig(*argv); 89275970Scy printf("%s\n", sys_signame[numsig]); 90275970Scy return (0); 91275970Scy } 92275970Scy printsignals(stdout); 93275970Scy return (0); 94275970Scy } 95275970Scy 96275970Scy if (!strcmp(*argv, "-s")) { 97293650Sglebius argc--, argv++; 98275970Scy if (argc < 1) { 99275970Scy warnx("option requires an argument -- s"); 100293650Sglebius usage(); 101275970Scy } 102275970Scy if (strcmp(*argv, "0")) { 103275970Scy if ((numsig = signame_to_signum(*argv)) < 0) 104275970Scy nosig(*argv); 105275970Scy } else 106275970Scy numsig = 0; 107275970Scy argc--, argv++; 108275970Scy } else if (**argv == '-' && *(*argv + 1) != '-') { 109275970Scy ++*argv; 110275970Scy if (isalpha(**argv)) { 111275970Scy if ((numsig = signame_to_signum(*argv)) < 0) 112275970Scy nosig(*argv); 113275970Scy } else if (isdigit(**argv)) { 114275970Scy numsig = strtol(*argv, &ep, 10); 115275970Scy if (!**argv || *ep) 116289997Sglebius errx(2, "illegal signal number: %s", *argv); 117289997Sglebius if (numsig < 0) 118289997Sglebius nosig(*argv); 119275970Scy } else 120275970Scy nosig(*argv); 121275970Scy argc--, argv++; 122275970Scy } 123275970Scy 124275970Scy if (argc > 0 && strncmp(*argv, "--", 2) == 0) 125275970Scy argc--, argv++; 126275970Scy 127275970Scy if (argc == 0) 128275970Scy usage(); 129275970Scy 130275970Scy for (errors = 0; argc; argc--, argv++) { 131275970Scy#ifdef SHELL 132275970Scy if (**argv == '%') 133275970Scy pid = getjobpgrp(*argv); 134275970Scy else 135275970Scy#endif 136275970Scy { 137275970Scy pid = strtol(*argv, &ep, 10); 138275970Scy if (!**argv || *ep) 139275970Scy errx(2, "illegal process id: %s", *argv); 140275970Scy } 141275970Scy if (kill(pid, numsig) == -1) { 142289997Sglebius warn("%s", *argv); 143289997Sglebius errors = 1; 144289997Sglebius } 145289997Sglebius } 146289997Sglebius 147289997Sglebius return (errors); 148289997Sglebius} 149289997Sglebius 150289997Sglebiusstatic int 151289997Sglebiussigname_to_signum(const char *sig) 152289997Sglebius{ 153289997Sglebius int n; 154289997Sglebius 155289997Sglebius if (!strncasecmp(sig, "sig", (size_t)3)) 156289997Sglebius sig += 3; 157289997Sglebius for (n = 1; n < sys_nsig; n++) { 158275970Scy if (!strcasecmp(sys_signame[n], sig)) 159275970Scy return (n); 160275970Scy } 161275970Scy return (-1); 162275970Scy} 163275970Scy 164275970Scystatic void 165275970Scynosig(const char *name) 166275970Scy{ 167275970Scy 168275970Scy warnx("unknown signal %s; valid signals:", name); 169275970Scy printsignals(stderr); 170275970Scy#ifdef SHELL 171275970Scy error(NULL); 172275970Scy#else 173275970Scy exit(2); 174275970Scy#endif 175275970Scy} 176275970Scy 177275970Scystatic void 178275970Scyprintsignals(FILE *fp) 179275970Scy{ 180275970Scy int n; 181275970Scy 182275970Scy for (n = 1; n < sys_nsig; n++) { 183275970Scy (void)fprintf(fp, "%s", sys_signame[n]); 184275970Scy if (n == (sys_nsig / 2) || n == (sys_nsig - 1)) 185275970Scy (void)fprintf(fp, "\n"); 186275970Scy else 187275970Scy (void)fprintf(fp, " "); 188275970Scy } 189316722Sdelphij} 190316722Sdelphij 191316722Sdelphijstatic void 192275970Scyusage(void) 193275970Scy{ 194275970Scy 195275970Scy (void)fprintf(stderr, "%s\n%s\n%s\n%s\n", 196275970Scy "usage: kill [-s signal_name] pid ...", 197275970Scy " kill -l [exit_status]", 198275970Scy " kill -signal_name pid ...", 199275970Scy " kill -signal_number pid ..."); 200275970Scy#ifdef SHELL 201 error(NULL); 202#else 203 exit(2); 204#endif 205} 206