[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: fingerd





Hi,


These messages have been sent about fingerd.
My preference for fiddling with remote fingers is to
leave fingerd as supplied by the vendor (run by "nobody") and
replace the finger program itself.  It can be made to recognise
when it is being run by "nobody" and behave differently
from when run by another user.

Source at the end of this file.  (Bashed out fairly quickly
starting from a utmp-eraser I made for a luser who wouldn't
tolerate wall messages from shutdown.)

I have (among other things) an extension to TCP-wrappers
(a new hosts_access.c file), and a prog to find disk space wasted by duplicated files.  
(mail me with Subject: "send goodies" for these.)

 -- Peter Allan   [email protected]





Date: 23 Jan 1997 17:22:10 -0800
From: Steven L Baur <[email protected]>
> cfingerd is not a safe program.  It must run as root, and has some big
> problems.

> On Tue, 17 Sep 1996, Administrador da Rede wrote:
> > I use the newest version of cfinger, setted to not allow general finger, just
> > specific ones. Does anyone knows how this person did that ? I hope I can
> > find out, otherwise, bye bye finger service.

> Badly.
> I have sent the author a letter, but never got any reply back (it's 3
> months later now!), so I just take the opportunity to warn the public
> against its use.



/*  
*  
*  compile and test myfinger
*  
*  	cc  -C -o myfinger myfinger.c
*  
*  
*  (assuming the standard finger is /usr/ucb/finger)
*     cp /usr/ucb/finger /usr/ucb/finger.real
*     cp myfinger /usr/ucb/finger
*  
*  
*  (if using TCP wrapper reverse-fingers, make them NOT nobody,
*   but another id such as nobody2.)
*  
*  I disclaim any disasters........
*  
*/  

/*
 *
 *   my finger program - local only, to be less informative than /usr/ucb/finger
 *   
 */


#undef _utmp_h
#define TRUE  1
#define FALSE 0
#define FAKE 1
#define WIPE 2
#define UTMP "/etc/utmp"


#include <stdio.h>
#include <pwd.h>
#include "utmp.h"
#include <lastlog.h>

main(argc, argv, env)
int  argc;
char **argv;
char **env;
{
	int  i, listed;
	struct passwd *pwent;

	if (argc < 1)
		exit(0);	/* beat sneaks */

         /*  If run by "nobody" (uid=65534) assume this is a remote finger */
         /* otherwise run the standard finger command */
         if (65534!=getuid()) {
                       execv("/usr/ucb/finger.real", argv);
                       /** if we get here exec failed, so we default to my finger  **/
         }


	printf("Login       Name          Where\n");


	listed = 1;
	while ((pwent = getpwent()) != NULL) {

		if (argc > 1) {
		/*
		 * if there are args, and  name is NOT one of them, we skip
		 * it
		 */
			listed = 0;
			for (i = 1; (!listed) && (i < argc); i++) {
				if (!strcmp(argv[i], pwent->pw_name))
					listed = 1;
			}
		}
		if (listed)
			info(pwent);
	}

}


info(pwent)
struct passwd *pwent;
{
	long lpos;
	FILE *fp;
	int  i;
	struct utmp *sp;
	struct utmp utmpentry;
        char *login,*gecos;
      
        login=pwent->pw_name;
        gecos=pwent->pw_gecos;


	sp = &utmpentry;

	if ((fp = fopen(UTMP, "r")) == NULL) {
		fprintf(stderr, "failed to open utmp for reading\n");
		exit(1);
	}


	i = fseek(fp, 0, 0);
	if (i) {
		puts("failed to fseek start of file");
		exit(2);
	}

	do {
/* get current pos in file using ftell */
		lpos = ftell(fp);

/* fread the struct */
		fread(sp, sizeof utmpentry, 1, fp);


		if (!feof(fp)) {
			if (!strcmp(login, sp->ut_name)) {
				if (!nonuser(utmpentry)) {
                                        utmpentry.ut_host[15]='\0';
					printf("%s\t%s\t%s\t%s\n",login,gecos,sp->ut_line,sp->ut_host);
				}
			}
		}



/* on error we close & exit */
		if (ferror(fp)) {
			fprintf(stderr, " file error! so failed to find our session in utmp\n");
			fclose(fp);
			exit(3);
		}

	} while (!feof(fp));



	fclose(fp);

}
/* end */