/*
 * ident-spoofer.c, an authd/identd serivce emulator for fwtk
 * (C) Copyright 1998 by ArkanoiD <ark@eltex.ru>
 * Version 1.0beta
 *
 */

#include <stdio.h>
#include <syslog.h>
#include "firewall.h"

static  char                    riaddr[512];
static  char                    rladdr[512];
static  Cfg                     *confp;

oktotalkto()
{                       
        Cfg     *cf;
        int     x;
   
        cf = cfg_get("hosts",confp);
        while(cf != (Cfg *)0) {
                if(cf->argc < 1)
                        goto skip;

                for(x = 0; x < cf->argc && cf->argv[x][0] != '-'; x++) {
                        if(hostmatch(cf->argv[x],riaddr)) {
                                if(cf->flags & PERM_DENY) {
                                        syslog(LLEV,"deny host=%.512s/%.20s ident lookup",rladdr,riaddr);  
                                        return(0);
                                }
                                syslog(LLEV,"permit host=%.512s/%.20s ident lookup",rladdr,riaddr);
                                return(1);
                        }
                }
skip:
                cf = cfg_get("hosts",(Cfg*)0);
        } 
        syslog(LLEV,"deny host=%.512s/%.20s ident lookup",rladdr,riaddr);
        return(0);
}


main () 
{
	char		request[64];
	char		responce[128];
	int 		sport,dport;
	char		*tbuf;
	char		*ostype;
	Cfg		*cf;

#ifndef LOG_DAEMON
	openlog("ident-spoofer",LOG_PID);
#else
	openlog("ident-spoofer",LOG_PID|LOG_NDELAY,LFAC);
#endif

	if((confp = cfg_read("ident-spoofer")) == (Cfg *)-1)
		exit(1);
	if (peername(0,rladdr,riaddr,sizeof(rladdr))!= 0) {
		syslog (LLEV, "fwtksyserr: cannot get peer name: %m");
		exit(1);
	}
	if (!oktotalkto())
		exit(1);
	if(!fgets(request,sizeof(request),stdin)) {
		syslog(LLEV,"fwtksyserr: cannot read client socket");
		exit(1);
	}
		
	if ((cf = cfg_get("ostype",confp)) != (Cfg *)0) {
		if (cf->argc != 1) {
			syslog(LLEV,"fwtkcfgerr: ostype must have one parameter, line %d",cf->ln);
			exit(1);
		}
		ostype = cf->argv[0];
	} else	ostype = "UNIX";

	request[strlen(request)-2]=0;
	tbuf=(char *)strtok(request,",");
	if (tbuf)
		sport=atoi(tbuf);
	else
		syslog(LLEV,"malformed request");
	tbuf=(char *)strtok(NULL,",");	
	if (tbuf)
		dport=atoi(tbuf);
	else
		syslog(LLEV,"malformed request");

	cf = cfg_get("service",confp);
	while (cf != (Cfg *)0) {
		if ((cf->argc < 1) || (cf->argv[0][0] == '-')) {
			syslog(LLEV,"fwtkcfgerr: missing parameter, line %d",
			       cf->ln);
			exit(1);
		}
		if (str_to_port(cf->argv[0]) == dport) {
			sprintf(responce,"%d, %d : USERID : %s : %.20s",sport,
			       dport,ostype,cf->argv[1]);
			syslog(LLEV,"requested information granted: sp=%d dp=%d (user=%.20s service=%.20s)",sport,dport,cf->argv[1],cf->argv[0]);
			goto lookup_ok;
		}
		cf = cfg_get("service",(Cfg*)0);
	}

	syslog(LLEV,"service unknown, sp=%d dp=%d",sport,dport);
	sprintf(responce,"%d, %d : ERROR : HIDDEN-USER",sport,dport);

lookup_ok:

	puts(responce);
	exit(0);
}
	
