1/*
2 * This program is free software; you can redistribute it and/or
3 * modify it under the terms of the GNU General Public License as
4 * published by the Free Software Foundation; either version 2 of
5 * the License, or (at your option) any later version.
6 *
7 * This program is distributed in the hope that it will be useful,
8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10 * GNU General Public License for more details.
11 *
12 * You should have received a copy of the GNU General Public License
13 * along with this program; if not, write to the Free Software
14 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
15 * MA 02111-1307 USA
16 */
17/***************************************************************************
18 * LPRng - An Extended Print Spooler System
19 *
20 * Copyright 1988-2003, Patrick Powell, San Diego, CA
21 *     papowell@lprng.com
22 * See LICENSE for conditions of use.
23 *
24 ***************************************************************************/
25
26 static char *const _id =
27"$Id: proctitle.c,v 1.1.1.1 2008/10/15 03:28:27 james26_jang Exp $";
28
29#include "lp.h"
30#include "proctitle.h"
31/**** ENDINCLUDE ****/
32
33/*
34 *  SETPROCTITLE -- set process title for ps
35 *  proctitle( char *str );
36 *
37 *	Returns: none.
38 *
39 *	Side Effects: Clobbers argv of our main procedure so ps(1) will
40 * 		      display the title.
41 */
42
43/*
44 * From the Sendmail.8.8.8 Source Distribution
45 *
46 * Copyright (c) 1983, 1995-2000 Eric P. Allman
47 * Copyright (c) 1988, 1993
48 *	The Regents of the University of California.  All rights reserved.
49 *
50 * Redistribution and use in source and binary forms, with or without
51 * modification, are permitted provided that the following conditions
52 * are met:
53 * 1. Redistributions of source code must retain the above copyright
54 *    notice, this list of conditions and the following disclaimer.
55 * 2. Redistributions in binary form must reproduce the above copyright
56 *    notice, this list of conditions and the following disclaimer in the
57 *    documentation and/or other materials provided with the distribution.
58 * 3. All advertising materials mentioning features or use of this software
59 *    must display the following acknowledgement:
60 *	This product includes software developed by the University of
61 *	California, Berkeley and its contributors.
62 * 4. Neither the name of the University nor the names of its contributors
63 *    may be used to endorse or promote products derived from this software
64 *    without specific prior written permission.
65 *
66 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
67 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
68 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
69 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
70 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
71 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
72 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
73 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
74 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
75 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
76 * SUCH DAMAGE.
77 *
78 *	@(#)conf.h	8.335 (Berkeley) 10/24/97
79 */
80
81#ifdef __hpux
82# define SPT_TYPE	SPT_PSTAT
83#endif
84
85#if defined(_AIX32) || defined(_AIX) || defined(AIX) || defined(IS_AIX32)
86# define SPT_PADCHAR	'\0'	/* pad process title with nulls */
87#endif
88
89#ifdef	DGUX
90# define SPT_TYPE	SPT_NONE	/* don't use setproctitle */
91#endif
92
93#if defined(BSD4_4) && !defined(__bsdi__) && !defined(__GNU__)
94# define SPT_TYPE	SPT_PSSTRINGS	/* use PS_STRINGS pointer */
95#endif
96
97#ifdef __bsdi__
98# if defined(_BSDI_VERSION) && _BSDI_VERSION >= 199312
99#  undef SPT_TYPE
100#  define SPT_TYPE	SPT_BUILTIN	/* setproctitle is in libc */
101# else
102#  define SPT_PADCHAR	'\0'	/* pad process title with nulls */
103# endif
104#endif
105
106#if defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__)
107# if defined(__NetBSD__) && (NetBSD > 199307 || NetBSD0_9 > 1)
108#  undef SPT_TYPE
109#  define SPT_TYPE	SPT_BUILTIN	/* setproctitle is in libc */
110# endif
111# if defined(__FreeBSD__)
112#  undef SPT_TYPE
113#  if __FreeBSD__ >= 2
114#   include <osreldate.h>		/* and this works */
115#   if __FreeBSD_version >= 199512	/* 2.2-current right now */
116#    include <libutil.h>
117#    define SPT_TYPE	SPT_BUILTIN
118#   endif
119#  endif
120#  ifndef SPT_TYPE
121#   define SPT_TYPE	SPT_REUSEARGV
122#   define SPT_PADCHAR	'\0'		/* pad process title with nulls */
123#  endif
124# endif
125# if defined(__OpenBSD__)
126#  undef SPT_TYPE
127#  define SPT_TYPE	SPT_BUILTIN	/* setproctitle is in libc */
128# endif
129#endif
130
131#ifdef __GNU_HURD__
132# define SPT_TYPE	SPT_CHANGEARGV
133#endif /* GNU */
134
135/* SCO UNIX 3.2v4.0 Open Desktop 2.0 and earlier */
136#ifdef _SCO_unix_
137# define SPT_TYPE	SPT_SCO		/* write kernel u. area */
138#endif
139
140#ifdef __linux__
141# define SPT_PADCHAR	'\0'		/* pad process title with nulls */
142#endif
143
144#ifdef _SEQUENT_
145# define SPT_TYPE	SPT_NONE	/* don't use setproctitle */
146#endif
147
148#ifdef apollo
149# define SPT_TYPE	SPT_NONE	/* don't use setproctitle */
150#endif
151#ifdef NCR_MP_RAS2
152# define SPT_TYPE  SPT_NONE
153#endif
154
155#ifdef NCR_MP_RAS3
156# define SPT_TYPE 	SPT_NONE
157#endif
158/*
159**  SETPROCTITLE -- set process title for ps
160**
161**	Parameters:
162**		fmt -- a printf style format string.
163**		a, b, c -- possible parameters to fmt.
164**
165**	Returns:
166**		none.
167**
168**	Side Effects:
169**		Clobbers argv of our main procedure so ps(1) will
170**		display the title.
171*/
172
173#define SPT_NONE	0	/* don't use it at all */
174#define SPT_REUSEARGV	1	/* cover argv with title information */
175#define SPT_BUILTIN	2	/* use libc builtin */
176#define SPT_PSTAT	3	/* use pstat(PSTAT_SETCMD, ...) */
177#define SPT_PSSTRINGS	4	/* use PS_STRINGS->... */
178#define SPT_SYSMIPS	5	/* use sysmips() supported by NEWS-OS 6 */
179#define SPT_SCO		6	/* write kernel u. area */
180#define SPT_CHANGEARGV	7	/* write our own strings into argv[] */
181
182#ifndef SPT_TYPE
183# define SPT_TYPE	SPT_REUSEARGV
184#endif
185
186#if SPT_TYPE != SPT_NONE && SPT_TYPE != SPT_BUILTIN
187
188# if SPT_TYPE == SPT_PSTAT
189#  include <sys/pstat.h>
190# endif
191# if SPT_TYPE == SPT_PSSTRINGS
192#  include <machine/vmparam.h>
193#  include <sys/exec.h>
194#  ifndef PS_STRINGS	/* hmmmm....  apparently not available after all */
195#   undef SPT_TYPE
196#   define SPT_TYPE	SPT_REUSEARGV
197#  else
198#   ifndef NKPDE			/* FreeBSD 2.0 */
199#    define NKPDE 63
200 typedef unsigned int	*pt_entry_t;
201#   endif
202#  endif
203# endif
204
205# if SPT_TYPE == SPT_PSSTRINGS || SPT_TYPE == SPT_CHANGEARGV
206#  define SETPROC_STATIC	static
207# else
208#  define SETPROC_STATIC
209# endif
210
211# if SPT_TYPE == SPT_SYSMIPS
212#  include <sys/sysmips.h>
213#  include <sys/sysnews.h>
214# endif
215
216# if SPT_TYPE == SPT_SCO
217#  include <sys/immu.h>
218#  include <sys/dir.h>
219#  include <sys/user.h>
220#  include <sys/fs/s5param.h>
221#  if PSARGSZ > LINEBUFFER
222#   define SPT_BUFSIZE	PSARGSZ
223#  endif
224# endif
225
226# ifndef SPT_PADCHAR
227#  define SPT_PADCHAR	' '
228# endif
229
230# ifndef SPT_BUFSIZE
231#  define SPT_BUFSIZE	LINEBUFFER
232# endif
233
234#endif /* SPT_TYPE != SPT_NONE && SPT_TYPE != SPT_BUILTIN */
235
236/*
237**  Pointers for setproctitle.
238**	This allows "ps" listings to give more useful information.
239*/
240# if SPT_TYPE != SPT_BUILTIN
241 static char	**Argv = NULL;		/* pointer to argument vector */
242 static char	*LastArgv = NULL;	/* end of argv */
243#endif
244
245
246 void initsetproctitle(argc, argv, envp)
247	int argc;
248	char **argv;
249	char **envp;
250{
251# if SPT_TYPE != SPT_BUILTIN
252	register int i, envpsize = 0;
253	extern char **environ;
254
255	/*
256	**  Move the environment so setproctitle can use the space at
257	**  the top of memory.
258	*/
259
260	DEBUG1("initsetproctitle: doing setup");
261	for (i = 0; envp[i] != NULL; i++)
262		envpsize += safestrlen(envp[i]) + 1;
263	{
264	char *s;
265	environ = (char **) malloc_or_die((sizeof (char *) * (i + 1))+envpsize+1,__FILE__,__LINE__);
266	s = ((char *)environ)+((sizeof (char *) * (i + 1)));
267	for (i = 0; envp[i] != NULL; i++){
268		strcpy(s,envp[i]);
269		environ[i] = s;
270		s += safestrlen(s)+1;
271	}
272	}
273	environ[i] = NULL;
274
275	/*
276	**  Save start and extent of argv for setproctitle.
277	*/
278
279	Argv = argv;
280
281	/*
282	**  Determine how much space we can use for setproctitle.
283	**  Use all contiguous argv and envp pointers starting at argv[0]
284 	*/
285	for (i = 0; i < argc; i++)
286	{
287		if (i==0 || LastArgv + 1 == argv[i])
288			LastArgv = argv[i] + safestrlen(argv[i]);
289		else
290			continue;
291	}
292	for (i=0; envp[i] != NULL; i++)
293	{
294		if (LastArgv + 1 == envp[i])
295			LastArgv = envp[i] + safestrlen(envp[i]);
296		else
297			continue;
298	}
299	DEBUG1("initsetproctitle: Argv 0x%lx, LastArgv 0x%lx", Argv, LastArgv);
300#else
301	DEBUG1("initsetproctitle: using builtin");
302#endif
303}
304
305#if SPT_TYPE != SPT_BUILTIN
306
307 void
308#ifdef HAVE_STDARGS
309 setproctitle (const char *fmt,...)
310#else
311 setproctitle (va_alist) va_dcl
312#endif
313
314{
315# if SPT_TYPE != SPT_NONE
316	register int i;
317	SETPROC_STATIC char buf[SPT_BUFSIZE];
318#  if SPT_TYPE == SPT_PSTAT
319	union pstun pst;
320#  endif
321#  if SPT_TYPE == SPT_SCO
322	off_t seek_off;
323	static int kmem = -1;
324	static int kmempid = -1;
325	struct user u;
326#  endif
327
328    VA_LOCAL_DECL
329    /* print the argument string */
330    VA_START (fmt);
331    VA_SHIFT (fmt, char *);
332    (void) VSNPRINTF(buf, sizeof(buf)) fmt, ap);
333    VA_END;
334
335	i = safestrlen(buf);
336
337#  if SPT_TYPE == SPT_PSTAT
338	pst.pst_command = buf;
339	pstat(PSTAT_SETCMD, pst, i, 0, 0);
340#  endif
341#  if SPT_TYPE == SPT_PSSTRINGS
342	PS_STRINGS->ps_nargvstr = 1;
343	PS_STRINGS->ps_argvstr = buf;
344#  endif
345#  if SPT_TYPE == SPT_SYSMIPS
346	sysmips(SONY_SYSNEWS, NEWS_SETPSARGS, buf);
347#  endif
348#  if SPT_TYPE == SPT_SCO
349	if (kmem < 0 || kmempid != getpid())
350	{
351		if (kmem >= 0)
352			close(kmem);
353		kmem = open(_PATH_KMEM, O_RDWR, 0);
354		if (kmem < 0)
355			return;
356		(void) fcntl(kmem, F_SETFD, 1);
357		kmempid = getpid();
358	}
359	buf[PSARGSZ - 1] = '\0';
360	seek_off = UVUBLK + (off_t) u.u_psargs - (off_t) &u;
361	if (lseek(kmem, (off_t) seek_off, SEEK_SET) == seek_off)
362		(void) write(kmem, buf, PSARGSZ);
363#  endif
364#  if SPT_TYPE == SPT_REUSEARGV
365	if (i > LastArgv - Argv[0] - 2)
366	{
367		i = LastArgv - Argv[0] - 2;
368		buf[i] = '\0';
369	}
370	(void) strcpy(Argv[0], buf);
371	{ char *p;
372	p = &Argv[0][i];
373	while (p < LastArgv)
374		*p++ = SPT_PADCHAR;
375	}
376	Argv[1] = NULL;
377#  endif
378#  if SPT_TYPE == SPT_CHANGEARGV
379	Argv[0] = buf;
380	Argv[1] = 0;
381#  endif
382# endif /* SPT_TYPE != SPT_NONE */
383}
384
385#endif /* SPT_TYPE != SPT_BUILTIN */
386