⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 filter.c

📁 <B>Digital的Unix操作系统VAX 4.2源码</B>
💻 C
📖 第 1 页 / 共 2 页
字号:
#ifndef lintstatic char *sccsid = "@(#)filter.c	4.2      ULTRIX 	10/16/90";#endif/************************************************************************ *									* *			Copyright (c) 1988 by				* *		Digital Equipment Corporation, Maynard, MA		* *			All rights reserved.				* *									* *   This software is furnished under a license and may be used and	* *   copied  only  in accordance with the terms of such license and	* *   with the  inclusion  of  the  above  copyright  notice.   This	* *   software  or  any  other copies thereof may not be provided or	* *   otherwise made available to any other person.  No title to and	* *   ownership of the software is hereby transferred.			* *									* *   The information in this software is subject to change  without	* *   notice  and should not be construed as a commitment by Digital	* *   Equipment Corporation.						* *									* *   Digital assumes no responsibility for the use  or  reliability	* *   of its software on equipment which is not supplied by Digital.	* *									* ************************************************************************//* * filter.c -- filter argument collection and execution * * Description: *	This file is the implementation of an object to *	describe filter programs to be run as sub-shells. * *	A filter is a pipeline of simple commands. *	Each simple command can be specified with *	an arbitrary number of arguments. *	There is a restriction on the number of simple *	commands that may be specified in a pipeline. * *	Four calls are provided to add arguments to a *	particular component of a filter: fc_add_arg* *	See below for details. * #	The filter is run with fc_plumb_and_run. *	`Plumb' refers to setting up pipes if necessary. *	The call has arguments for passing the 3 file *	descriptors to be dup'ed for file descriptors 0, 1 and 2 *	in the filter. *	A special value FC_MAKEPIPE can be specified *	for any of these to indicate that a pipe should *	be set up to communicate with this file descriptor *	in the filter from the parent. *	The parent can find the file descriptor of such a *	pipe in the fc_fds field of the filter structure *	after fc_plumb_and_run has been called. *//* SCCS history beginning * *************************************************************** *                -- Revision History -- * *************************************************************** *  * 1.1  10/03/88 -- thoms * date and time created 88/03/10 14:01:09 by thoms *  * *************************************************************** *  * 1.2  22/03/88 -- thoms * Filter environment is inherited one except for PATH (from lp.local.h) *  *  * *************************************************************** *  * 1.3  30/03/88 -- thoms * Basic PostScript job building and execution working *  *  * *************************************************************** *  * 1.4  25/04/88 -- thoms * Additional check in filter stop code, more debug logging in fc_run *  *  * *************************************************************** *  * 1.5  29/04/88 -- thoms * More debugging in fc_wait() *  *  * *************************************************************** *  * 1.6  03/05/88 -- thoms * Fixed and stable, minimal PS functionality. *  *  * *************************************************************** *  * 1.7  20/05/88 -- thoms * fc_pout_run now has dofork argument to determine behaviour on * repeated fork failure *  *  * *************************************************************** * * 1.8 15/07/88 -- thoms * Added copyright notice and modification history, more comments * Improved some names * * *************************************************************** * * 1.9  19/07/88 -- thoms * Fixed a typo * * *************************************************************** * * 1.10  28/07/88 -- thoms * Generalised piping to filters and replaced the exported * calls fc_run and fc_pout_run with generalised function * fc_plumb_and_run which opens up pipes as required to * the spawned filter. * Added code to fc_init, fc_delete and fc_wait to cope * with parasitic linked on filter.  Needed for pt_lps_v3. * * *************************************************************** * * 1.11  01/09/88 -- thoms * Added fc_start function to restart filters, tidied up fc_stop * Cleaned up and improved diagnostics in fc_wait * * *************************************************************** * * 1.12  09/09/88 -- thoms * Added more debug logging to in fc_wait * * *************************************************************** * * 1.13  09/09/88 -- thoms * Fixed status zeroing bug in fc_wait * * *************************************************************** * * 1.14   2/08/89 -- Giles Atkinson * Added calls to monitor progress while printing. * * SCCS history end */#include "lp.h"/* Declaration of local function */static char **chenv(/* char **env, envstr */);static void fc_run(/* register FCP fcp; int fork_action; */);static int dofork(/* int action_on_fail */);/* for exported functions declarations see filter.h *//* * dofork - fork with retries on failure */static intdofork(action)int action;{	register int i, pid;	for (i = 0; i < DOFORK_NRETRIES; i++) {		if ((pid = fork()) < 0) {			sleep((unsigned)(i*i));			continue;		}		/*		 * Child should run as daemon instead of root		 */		if (pid == 0)			if (setuid(DU) < 0) {				log("setuid to %d failed", DU);				exit(1);			}		return(pid);	}	log("can't fork");	switch (action) {	case DORETURN:		return (-1);	default:		log("bad action (%d) to dofork", action);		/*FALL THRU*/	case DOABORT:		exit(1);	}	/*NOTREACHED*/}/* * strsave -- save string using malloc, spotting null pointers */char *strsave(str)char *str;{	register char *saved;	static char *null_string = "<null-string>";	if (!str) {		str = null_string;	}	saved = malloc((unsigned)strlen(str) + 1);	strcpy(saved, str);	return saved;}/* * printv -- print a vector of strings in a standard format to stderr */voidprintv(argv)char **argv;{	while (*argv) fprintf(stderr, "\"%s\" ", *argv++);}/* * chenv -- replace an environment string * * This should only be called in a sub-process and * only after fork, not vfork * * Return values: *	Returns pointer to environ vector on success *	0 on failure to find particular env variable * Future improvement: *	Could build new environment vector to add new *	environment variables */static char **chenv(env, envstr)char **env;char *envstr;{	register char *vardelim;	register char **envp;	register int envstrlen;	if (!(vardelim = strchr(envstr, '='))) return 0;	envstrlen = vardelim - envstr;	for (envp = env; *envp; envp++) {		if (!strncmp(*envp, envstr, envstrlen)) {			*envp = envstr;			return env;		}	}	/* could extend env vector by mallocing one day */	return 0;}/* * parse_prog -- perform shell-like parsing of string into filter * * Return values: *	Returns pointer to next non-white or 0 if end of string */char *parse_prog(fcp, prog_str)register FCP fcp;		/* resulting args put here */char *prog_str;		/* input string */{	register char *retp, *s, *prog = strsave(prog_str);	if (retp = strchr(prog, '|')) {		*retp++ = '\0';		while (isspace(*retp)) retp++;		if (!*retp) {			retp = 0;		} else {	/* fix up to point into supplied string */			retp -= (prog - prog_str);		}	}	for (s=strtok(prog, " \t"); s; s=strtok(NULL, " \t")) {		fc_add_arg(fcp, s);	}	fc_end_filter(fcp);	free(prog);	return retp;}/* * fc_grow -- make room for more arguments in filter object */static voidfc_grow(fcp)register FCP fcp;{	register char **p, **plim;	register unsigned newsiz = (fcp->fc_i + FC_CLICK);	newsiz /= FC_CLICK;	newsiz *= FC_CLICK;	fcp->fc_argv[fcp->fc_nf] =	    ((fcp->fc_argv[fcp->fc_nf])	     ? (char **)realloc((char *)fcp->fc_argv[fcp->fc_nf],				newsiz*sizeof(char *))	     : (char **)malloc(newsiz*sizeof(char *)));	plim = &fcp->fc_argv[fcp->fc_nf][newsiz];	for (p = &fcp->fc_argv[fcp->fc_nf][fcp->fc_max]; p < plim; p++) {		*p = 0;	}	fcp->fc_max = newsiz;}/* * fc_next_simple_command_init -- init next filter component description */static voidfc_next_simple_command_init(fcp)register FCP fcp;{		fcp->fc_i = 0;	fcp->fc_max = 0;	fc_grow(fcp);}/* * fc_init -- initialise filter chain structure */void fc_init(fcp)register FCP fcp;{	register int i;	memset(fcp, '\0', sizeof(*fcp));	for (i = 0; i < 3; i++) {		fcp->fc_fds[i] = FC_FD_CLOSED;	}	for (i = 0; i < FC_MAX_SIMPLE_COMMANDS; i++ ) {		fcp->fc_pid[i] = -1;	}	fc_next_simple_command_init(fcp);}/* * new_fc -- allocate filter object and initialise */FCPnew_fc(){	register FCP new_fcp;	new_fcp = (FCP)malloc(sizeof(*new_fcp));	fc_init(new_fcp);	return new_fcp;}/* * fc_delete -- delete filter object */void fc_delete(fcp, on_heap)FCP fcp;int on_heap;			/* was malloc'ed if non-zero */{	register int i;	/*	 * If we had any pipes set up to the filter make	 * sure they're closed down	 */	for (i=0; i < 3; i++) {		if (fcp->fc_is_pipe & (1<<i) && fcp->fc_fds[i] >= 0) {			(void) close(fcp->fc_fds[i]);			fcp->fc_fds[i] = FC_FD_CLOSED;		}	}	for (i = 0; i <= fcp->fc_nf; i++) {		register char **p, **pv;		if (!(pv = fcp->fc_argv[i])) continue;		for (p = pv; *p; p++) free(*p);		free((char *)pv);	}	if (fcp->fc_next) fc_delete(fcp->fc_next, 1);	if (on_heap) free((char *)fcp);}/* * fc_end_filter -- terminate current simple command description */voidfc_end_filter(fcp)register FCP fcp;{	assert(fcp->fc_nf <= FC_MAX_SIMPLE_COMMANDS);	if (fcp->fc_i >= fcp->fc_max) {		fc_grow(fcp);	}	fcp->fc_argv[fcp->fc_nf++][fcp->fc_i] = 0;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -