/* $Id: isdn_divert.c,v 1.6.6.3 2001/09/23 22:24:36 kai Exp $
 *
 * DSS1 main diversion supplementary handling for i4l.
 *
 * Copyright 1999       by Werner Cornelius (werner@isdn4linux.de)
 *
 * This software may be used and distributed according to the terms
 * of the GNU General Public License, incorporated herein by reference.
 *
 */

#include <linux/proc_fs.h>
#include <linux/slab.h>
#include <linux/timer.h>
#include <linux/jiffies.h>

#include "isdn_divert.h"

/**********************************/
/* structure keeping calling info */
/**********************************/
struct call_struc {
	isdn_ctrl ics; /* delivered setup + driver parameters */
	ulong divert_id; /* Id delivered to user */
	unsigned char akt_state; /* actual state */
	char deflect_dest[35]; /* deflection destination */
	struct timer_list timer; /* timer control structure */
	char info[90]; /* device info output */
	struct call_struc *next; /* pointer to next entry */
	struct call_struc *prev;
};


/********************************************/
/* structure keeping deflection table entry */
/********************************************/
struct deflect_struc {
	struct deflect_struc *next, *prev;
	divert_rule rule; /* used rule */
};


/*****************************************/
/* variables for main diversion services */
/*****************************************/
/* diversion/deflection processes */
static struct call_struc *divert_head = NULL; /* head of remembered entrys */
static ulong next_id = 1; /* next info id */
static struct deflect_struc *table_head = NULL;
static struct deflect_struc *table_tail = NULL;
static unsigned char extern_wait_max = 4; /* maximum wait in s for external process */

DEFINE_SPINLOCK(divert_lock);

/***************************/
/* timer callback function */
/***************************/
static void deflect_timer_expire(ulong arg)
{
	unsigned long flags;
	struct call_struc *cs = (struct call_struc *) arg;

	spin_lock_irqsave(&divert_lock, flags);
	del_timer(&cs->timer); /* delete active timer */
	spin_unlock_irqrestore(&divert_lock, flags);

	switch (cs->akt_state) {
	case DEFLECT_PROCEED:
		cs->ics.command = ISDN_CMD_HANGUP; /* cancel action */
		divert_if.ll_cmd(&cs->ics);
		spin_lock_irqsave(&divert_lock, flags);
		cs->akt_state = DEFLECT_AUTODEL; /* delete after timeout */
		cs->timer.expires = jiffies + (HZ * AUTODEL_TIME);
		add_timer(&cs->timer);
		spin_unlock_irqrestore(&divert_lock, flags);
		break;

	case DEFLECT_ALERT:
		cs->ics.command = ISDN_CMD_REDIR; /* protocol */
		strlcpy(cs->ics.parm.setup.phone, cs->deflect_dest, sizeof(cs->ics.parm.setup.phone));
		strcpy(cs->ics.parm.setup.eazmsn, "Testtext delayed");
		divert_if.ll_cmd(&cs->ics);
		spin_lock_irqsave(&divert_lock, flags);
		cs->akt_state = DEFLECT_AUTODEL; /* delete after timeout */
		cs->timer.expires = jiffies + (HZ * AUTODEL_TIME);
		add_timer(&cs->timer);
		spin_unlock_irqrestore(&divert_lock, flags);
		break;

	case DEFLECT_AUTODEL:
	default:
		spin_lock_irqsave(&divert_lock, flags);
		if (cs->prev)
			cs->prev->next = cs->next; /* forward link */
		else
			divert_head = cs->next;
		if (cs->next)
			cs->next->prev = cs->prev; /* back link */
		spin_unlock_irqrestore(&divert_lock, flags);
		kfree(cs);
		return;

	} /* switch */
} /* deflect_timer_func */


/*****************************************/
/* handle call forwarding de/activations */
/* 0 = deact, 1 = act, 2 = interrogate   */
/*****************************************/
int cf_command(int drvid, int mode,
	       u_char proc, char *msn,
	       u_char service, char *fwd_nr, ulong *procid)
{
	unsigned long flags;
	int retval, msnlen;
	int fwd_len;
	char *p, *ielenp, tmp[60];
	struct call_struc *cs;

	if (strchr(msn, '.')) return (-EINVAL); /* subaddress not allowed in msn */
	if ((proc & 0x7F) > 2) return (-EINVAL);
	proc &= 3;
	p = tmp;
	*p++ = 0x30; /* enumeration */
	ielenp = p++; /* remember total length position */
	*p++ = 0xa; /* proc tag */
	*p++ = 1;   /* length */
	*p++ = proc & 0x7F; /* procedure to de/activate/interrogate */
	*p++ = 0xa; /* service tag */
	*p++ = 1;   /* length */
	*p++ = service; /* service to handle */

	if (mode == 1) {
		if (!*fwd_nr) return (-EINVAL); /* destination missing */
		if (strchr(fwd_nr, '.')) return (-EINVAL); /* subaddress not allowed */
		fwd_len = strlen(fwd_nr);
		*p++ = 0x30; /* number enumeration */
		*p++ = fwd_len + 2; /* complete forward to len */
		*p++ = 0x80; /* fwd to nr */
		*p++ = fwd_len; /* length of number */
		strcpy(p, fwd_nr); /* copy number */
		p += fwd_len; /* pointer beyond fwd */
	} /* activate */

	msnlen = strlen(msn);
	*p++ = 0x80; /* msn number */
	if (msnlen > 1) {
		*p++ = msnlen; /* length */
		strcpy(p, msn);
		p += msnlen;
	} else
		*p++ = 0;

	*ielenp = p - ielenp - 1; /* set total IE length */

	/* allocate mem for information struct */
	if (!(cs = kmalloc(sizeof(struct call_struc), GFP_ATOMIC)))
		return (-ENOMEM); /* no memory */
	init_timer(&cs->timer);
	cs->info[0] = '\0';
	cs->timer.function = deflect_timer_expire;
	cs->timer.data = (ulong) cs; /* pointer to own structure */
	cs->ics.driver = drvid;
	cs->ics.command = ISDN_CMD_PROT_IO; /* protocol specific io */
	cs->ics.arg = DSS1_CMD_INVOKE; /* invoke supplementary service */
	cs->ics.parm.dss1_io.proc = (mode == 1) ? 7 : (mode == 2) ? 11 : 8; /* operation */
	cs->ics.parm.dss1_io.timeout = 4000; /* from ETS 300 207-1 */
	cs->ics.parm.dss1_io.datalen = p - tmp; /* total len */
	cs->ics.parm.dss1_io.data = tmp; /* start of buffer */

	spin_lock_irqsave(&divert_lock, flags);
	cs->ics.parm.dss1_io.ll_id = next_id++; /* id for callback */
	spin_unlock_irqrestore(&divert_lock, flags);
	*procid = cs->ics.parm.dss1_io.ll_id;

	sprintf(cs->info, "%d 0x%lx %s%s 0 %s %02x %d%s%s\n",
		(!mode) ? DIVERT_DEACTIVATE : (mode == 1) ? DIVERT_ACTIVATE : DIVERT_REPORT,
		cs->ics.parm.dss1_io.ll_id,
		(mode != 2) ? "" : "0 ",
		divert_if.drv_to_name(cs->ics.driver),
		msn,
		service & 0xFF,
		proc,
		(mode != 1) ? "" : " 0 ",
		(mode != 1) ? "" : fwd_nr);

	retval = divert_if.ll_cmd(&cs->ics); /* execute command */

	if (!retval) {
		cs->prev = NULL;
		spin_lock_irqsave(&divert_lock, flags);
		cs->next = divert_head;
		divert_head = cs;
		spin_unlock_irqrestore(&divert_lock, flags);
	} else
		kfree(cs);
	return (retval);
} /* cf_command */


/****************************************/
/* handle a external deflection command */
/****************************************/
int deflect_extern_action(u_char cmd, ulong callid, char *to_nr)
{
	struct call_struc *cs;
	isdn_ctrl ic;
	unsigned long flags;
	int i;

	if ((cmd & 0x7F) > 2) return (-EINVAL); /* invalid command */
	cs = divert_head; /* start of parameter list */
	while (cs) {
		if (cs->divert_id == callid) break; /* found */
		cs = cs->next;
	} /* search entry */
	if (!cs) return (-EINVAL); /* invalid callid */

	ic.driver = cs->ics.driver;
	ic.arg = cs->ics.arg;
	i = -EINVAL;
	if (cs->akt_state == DEFLECT_AUTODEL) return (i); /* no valid call */
	switch (cmd & 0x7F) {
	case 0: /* hangup */
		del_timer(&cs->timer);
		ic.command = ISDN_CMD_HANGUP;
		i = divert_if.ll_cmd(&ic);
		spin_lock_irqsave(&divert_lock, flags);
		cs->akt_state = DEFLECT_AUTODEL; /* delete after timeout */
		cs->timer.expires = jiffies + (HZ * AUTODEL_TIME);
		add_timer(&cs->timer);
		spin_unlock_irqrestore(&divert_lock, flags);
		break;

	case 1: /* alert */
		if (cs->akt_state == DEFLECT_ALERT) return (0);
		cmd &= 0x7F; /* never wait */
		del_timer(&cs->timer);
		ic.command = ISDN_CMD_ALERT;
		if ((i = divert_if.ll_cmd(&ic))) {
			spin_lock_irqsave(&divert_lock, flags);
			cs->akt_state = DEFLECT_AUTODEL; /* delete after timeout */
			cs->timer.expires = jiffies + (HZ * AUTODEL_TIME);
			add_timer(&cs->timer);
			spin_unlock_irqrestore(&divert_lock, flags);
		} else
			cs->akt_state = DEFLECT_ALERT;
		break;

	case 2: /* redir */
		del_timer(&cs->timer);
		strlcpy(cs->ics.parm.setup.phone, to_nr, sizeof(cs->ics.parm.setup.phone));
		strcpy(cs->ics.parm.setup.eazmsn, "Testtext manual");
		ic.command = ISDN_CMD_REDIR;
		if ((i = divert_if.ll_cmd(&ic))) {
			spin_lock_irqsave(&divert_lock, flags);
			cs->akt_state = DEFLECT_AUTODEL; /* delete after timeout */
			cs->timer.expires = jiffies + (HZ * AUTODEL_TIME);
			add_timer(&cs->timer);
			spin_unlock_irqrestore(&divert_lock, flags);
		} else
			cs->akt_state = DEFLECT_ALERT;
		break;

	} /* switch */
	return (i);
} /* deflect_extern_action */

/********************************/
/* insert a new rule before idx */
/********************************/
int insertrule(int idx, divert_rule *newrule)
{
	struct deflect_struc *ds, *ds1 = NULL;
	unsigned long flags;

	if (!(ds = kmalloc(sizeof(struct deflect_struc), GFP_KERNEL)))
		return (-ENOMEM); /* no memory */

	ds->rule = *newrule; /* set rule */

	spin_lock_irqsave(&divert_lock, flags);

	if (idx >= 0) {
		ds1 = table_head;
		while ((ds1) && (idx > 0))
		{ idx--;
			ds1 = ds1->next;
		}
		if (!ds1) idx = -1;
	}

	if (idx < 0) {
		ds->prev = table_tail; /* previous entry */
		ds->next = NULL; /* end of chain */
		if (ds->prev)
			ds->prev->next = ds; /* last forward */
		else
			table_head = ds; /* is first entry */
		table_tail = ds; /* end of queue */
	} else {
		ds->next = ds1; /* next entry */
		ds->prev = ds1->prev; /* prev entry */
		ds1->prev = ds; /* backward chain old element */
		if (!ds->prev)
			table_head = ds; /* first element */
	}

	spin_unlock_irqrestore(&divert_lock, flags);
	return (0);
} /* insertrule */

/***********************************/
/* delete the rule at position idx */
/***********************************/
int deleterule(int idx)
{
	struct deflect_struc *ds, *ds1;
	unsigned long flags;

	if (idx < 0) {
		spin_lock_irqsave(&divert_lock, flags);
		ds = table_head;
		table_head = NULL;
		table_tail = NULL;
		spin_unlock_irqrestore(&divert_lock, flags);
		while (ds) {
			ds1 = ds;
			ds = ds->next;
			kfree(ds1);
		}
		return (0);
	}

	spin_lock_irqsave(&divert_lock, flags);
	ds = table_head;

	while ((ds) && (idx > 0)) {
		idx--;
		ds = ds->next;
	}

	if (!ds) {
		spin_unlock_irqrestore(&divert_lock, flags);
		return (-EINVAL);
	}

	if (ds->next)
		ds->next->prev = ds->prev; /* backward chain */
	else
		table_tail = ds->prev; /* end of chain */

	if (ds->prev)
		ds->prev->next = ds->next; /* forward chain */
	else
		table_head = ds->next; /* start of chain */

	spin_unlock_irqrestore(&divert_lock, flags);
	kfree(ds);
	return (0);
} /* deleterule */

/*******************************************/
/* get a pointer to a specific rule number */
/*******************************************/
divert_rule *getruleptr(int idx)
{
	struct deflect_struc *ds = table_head;

	if (idx < 0) return (NULL);
	while ((ds) && (idx >= 0)) {
		if (!(idx--)) {
			return (&ds->rule);
			break;
		}
		ds = ds->next;
	}
	return (NULL);
} /* getruleptr */

/*************************************************/
/* called from common module on an incoming call */
/*************************************************/
static int isdn_divert_icall(isdn_ctrl *ic)
{
	int retval = 0;
	unsigned long flags;
	struct call_struc *cs = NULL;
	struct deflect_struc *dv;
	char *p, *p1;
	u_char accept;

	/* first check the internal deflection table */
	for (dv = table_head; dv; dv = dv->next) {
		/* scan table */
		if (((dv->rule.callopt == 1) && (ic->command == ISDN_STAT_ICALLW)) ||
		    ((dv->rule.callopt == 2) && (ic->command == ISDN_STAT_ICALL)))
			continue; /* call option check */
		if (!(dv->rule.drvid & (1L << ic->driver)))
			continue; /* driver not matching */
		if ((dv->rule.si1) && (dv->rule.si1 != ic->parm.setup.si1))
			continue; /* si1 not matching */
		if ((dv->rule.si2) && (dv->rule.si2 != ic->parm.setup.si2))
			continue; /* si2 not matching */

		p = dv->rule.my_msn;
		p1 = ic->parm.setup.eazmsn;
		accept = 0;
		while (*p) {
			/* complete compare */
			if (*p == '-') {
				accept = 1; /* call accepted */
				break;
			}
			if (*p++ != *p1++)
				break; /* not accepted */
			if ((!*p) && (!*p1))
				accept = 1;
		} /* complete compare */
		if (!accept) continue; /* not accepted */

		if ((strcmp(dv->rule.caller, "0")) ||
		    (ic->parm.setup.phone[0])) {
			p = dv->rule.caller;
			p1 = ic->parm.setup.phone;
			accept = 0;
			while (*p) {
				/* complete compare */
				if (*p == '-') {
					accept = 1; /* call accepted */
					break;
				}
				if (*p++ != *p1++)
					break; /* not accepted */
				if ((!*p) && (!*p1))
					accept = 1;
			} /* complete compare */
			if (!accept) continue; /* not accepted */
		}

		switch (dv->rule.action) {
		case DEFLECT_IGNORE:
			return 0;

		case DEFLECT_ALERT:
		case DEFLECT_PROCEED:
		case DEFLECT_REPORT:
		case DEFLECT_REJECT:
			if (dv->rule.action == DEFLECT_PROCEED)
				if ((!if_used) || ((!extern_wait_max) && (!dv->rule.waittime)))
					return (0); /* no external deflection needed */
			if (!(cs = kmalloc(sizeof(struct call_struc), GFP_ATOMIC)))
				return (0); /* no memory */
			init_timer(&cs->timer);
			cs->info[0] = '\0';
			cs->timer.function = deflect_timer_expire;
			cs->timer.data = (ulong) cs; /* pointer to own structure */

			cs->ics = *ic; /* copy incoming data */
			if (!cs->ics.parm.setup.phone[0]) strcpy(cs->ics.parm.setup.phone, "0");
			if (!cs->ics.parm.setup.eazmsn[0]) strcpy(cs->ics.parm.setup.eazmsn, "0");
			cs->ics.parm.setup.screen = dv->rule.screen;
			if (dv->rule.waittime)
				cs->timer.expires = jiffies + (HZ * dv->rule.waittime);
			else if (dv->rule.action == DEFLECT_PROCEED)
				cs->timer.expires = jiffies + (HZ * extern_wait_max);
			else
				cs->timer.expires = 0;
			cs->akt_state = dv->rule.action;
			spin_lock_irqsave(&divert_lock, flags);
			cs->divert_id = next_id++; /* new sequence number */
			spin_unlock_irqrestore(&divert_lock, flags);
			cs->prev = NULL;
			if (cs->akt_state == DEFLECT_ALERT) {
				strcpy(cs->deflect_dest, dv->rule.to_nr);
				if (!cs->timer.expires) {
					strcpy(ic->parm.setup.eazmsn,
					       "Testtext direct");
					ic->parm.setup.screen = dv->rule.screen;
					strlcpy(ic->parm.setup.phone, dv->rule.to_nr, sizeof(ic->parm.setup.phone));
					cs->akt_state = DEFLECT_AUTODEL; /* delete after timeout */
					cs->timer.expires = jiffies + (HZ * AUTODEL_TIME);
					retval = 5;
				} else
					retval = 1; /* alerting */
			} else {
				cs->deflect_dest[0] = '\0';
				retval = 4; /* only proceed */
			}
			sprintf(cs->info, "%d 0x%lx %s %s %s %s 0x%x 0x%x %d %d %s\n",
				cs->akt_state,
				cs->divert_id,
				divert_if.drv_to_name(cs->ics.driver),
				(ic->command == ISDN_STAT_ICALLW) ? "1" : "0",
				cs->ics.parm.setup.phone,
				cs->ics.parm.setup.eazmsn,
				cs->ics.parm.setup.si1,
				cs->ics.parm.setup.si2,
				cs->ics.parm.setup.screen,
				dv->rule.waittime,
				cs->deflect_dest);
			if ((dv->rule.action == DEFLECT_REPORT) ||
			    (dv->rule.action == DEFLECT_REJECT)) {
				put_info_buffer(cs->info);
				kfree(cs); /* remove */
				return ((dv->rule.action == DEFLECT_REPORT) ? 0 : 2); /* nothing to do */
			}
			break;

		default:
			return 0; /* ignore call */
		} /* switch action */
		break; /* will break the 'for' looping */
	} /* scan_table */

	if (cs) {
		cs->prev = NULL;
		spin_lock_irqsave(&divert_lock, flags);
		cs->next = divert_head;
		divert_head = cs;
		if (cs->timer.expires) add_timer(&cs->timer);
		spin_unlock_irqrestore(&divert_lock, flags);

		put_info_buffer(cs->info);
		return (retval);
	} else
		return (0);
} /* isdn_divert_icall */


void deleteprocs(void)
{
	struct call_struc *cs, *cs1;
	unsigned long flags;

	spin_lock_irqsave(&divert_lock, flags);
	cs = divert_head;
	divert_head = NULL;
	while (cs) {
		del_timer(&cs->timer);
		cs1 = cs;
		cs = cs->next;
		kfree(cs1);
	}
	spin_unlock_irqrestore(&divert_lock, flags);
} /* deleteprocs */

/****************************************************/
/* put a address including address type into buffer */
/****************************************************/
static int put_address(char *st, u_char *p, int len)
{
	u_char retval = 0;
	u_char adr_typ = 0; /* network standard */

	if (len < 2) return (retval);
	if (*p == 0xA1) {
		retval = *(++p) + 2; /* total length */
		if (retval > len) return (0); /* too short */
		len = retval - 2; /* remaining length */
		if (len < 3) return (0);
		if ((*(++p) != 0x0A) || (*(++p) != 1)) return (0);
		adr_typ = *(++p);
		len -= 3;
		p++;
		if (len < 2) return (0);
		if (*p++ != 0x12) return (0);
		if (*p > len) return (0); /* check number length */
		len = *p++;
	} else if (*p == 0x80) {
		retval = *(++p) + 2; /* total length */
		if (retval > len) return (0);
		len = retval - 2;
		p++;
	} else
		return (0); /* invalid address information */

	sprintf(st, "%d ", adr_typ);
	st += strlen(st);
	if (!len)
		*st++ = '-';
	else
		while (len--)
			*st++ = *p++;
	*st = '\0';
	return (retval);
} /* put_address */

/*************************************/
/* report a successful interrogation */
/*************************************/
static int interrogate_success(isdn_ctrl *ic, struct call_struc *cs)
{
	char *src = ic->parm.dss1_io.data;
	int restlen = ic->parm.dss1_io.datalen;
	int cnt = 1;
	u_char n, n1;
	char st[90], *p, *stp;

	if (restlen < 2) return (-100); /* frame too short */
	if (*src++ != 0x30) return (-101);
	if ((n = *src++) > 0x81) return (-102); /* invalid length field */
	restlen -= 2; /* remaining bytes */
	if (n == 0x80) {
		if (restlen < 2) return (-103);
		if ((*(src + restlen - 1)) || (*(src + restlen - 2))) return (-104);
		restlen -= 2;
	} else if (n == 0x81) {
		n = *src++;
		restlen--;
		if (n > restlen) return (-105);
		restlen = n;
	} else if (n > restlen)
		return (-106);
	else
		restlen = n; /* standard format */
	if (restlen < 3) return (-107); /* no procedure */
	if ((*src++ != 2) || (*src++ != 1) || (*src++ != 0x0B)) return (-108);
	restlen -= 3;
	if (restlen < 2) return (-109); /* list missing */
	if (*src == 0x31) {
		src++;
		if ((n = *src++) > 0x81) return (-110); /* invalid length field */
		restlen -= 2; /* remaining bytes */
		if (n == 0x80) {
			if (restlen < 2) return (-111);
			if ((*(src + restlen - 1)) || (*(src + restlen - 2))) return (-112);
			restlen -= 2;
		} else if (n == 0x81) {
			n = *src++;
			restlen--;
			if (n > restlen) return (-113);
			restlen = n;
		} else if (n > restlen)
			return (-114);
		else
			restlen = n; /* standard format */
	} /* result list header */

	while (restlen >= 2) {
		stp = st;
		sprintf(stp, "%d 0x%lx %d %s ", DIVERT_REPORT, ic->parm.dss1_io.ll_id,
			cnt++, divert_if.drv_to_name(ic->driver));
		stp += strlen(stp);
		if (*src++ != 0x30) return (-115); /* invalid enum */
		n = *src++;
		restlen -= 2;
		if (n > restlen) return (-116); /* enum length wrong */
		restlen -= n;
		p = src; /* one entry */
		src += n;
		if (!(n1 = put_address(stp, p, n & 0xFF))) continue;
		stp += strlen(stp);
		p += n1;
		n -= n1;
		if (n < 6) continue; /* no service and proc */
		if ((*p++ != 0x0A) || (*p++ != 1)) continue;
		sprintf(stp, " 0x%02x ", (*p++) & 0xFF);
		stp += strlen(stp);
		if ((*p++ != 0x0A) || (*p++ != 1)) continue;
		sprintf(stp, "%d ", (*p++) & 0xFF);
		stp += strlen(stp);
		n -= 6;
		if (n > 2) {
			if (*p++ != 0x30) continue;
			if (*p > (n - 2)) continue;
			n = *p++;
			if (!(n1 = put_address(stp, p, n & 0xFF))) continue;
			stp += strlen(stp);
		}
		sprintf(stp, "\n");
		put_info_buffer(st);
	} /* while restlen */
	if (restlen) return (-117);
	return (0);
} /* interrogate_success */

/*********************************************/
/* callback for protocol specific extensions */
/*********************************************/
static int prot_stat_callback(isdn_ctrl *ic)
{
	struct call_struc *cs, *cs1;
	int i;
	unsigned long flags;

	cs = divert_head; /* start of list */
	cs1 = NULL;
	while (cs) {
		if (ic->driver == cs->ics.driver) {
			switch (cs->ics.arg) {
			case DSS1_CMD_INVOKE:
				if ((cs->ics.parm.dss1_io.ll_id == ic->parm.dss1_io.ll_id) &&
				    (cs->ics.parm.dss1_io.hl_id == ic->parm.dss1_io.hl_id)) {
					switch (ic->arg) {
					case DSS1_STAT_INVOKE_ERR:
						sprintf(cs->info, "128 0x%lx 0x%x\n",
							ic->parm.dss1_io.ll_id,
							ic->parm.dss1_io.timeout);
						put_info_buffer(cs->info);
						break;

					case DSS1_STAT_INVOKE_RES:
						switch (cs->ics.parm.dss1_io.proc) {
						case  7:
						case  8:
							put_info_buffer(cs->info);
							break;

						case  11:
							i = interrogate_success(ic, cs);
							if (i)
								sprintf(cs->info, "%d 0x%lx %d\n", DIVERT_REPORT,
									ic->parm.dss1_io.ll_id, i);
							put_info_buffer(cs->info);
							break;

						default:
							printk(KERN_WARNING "dss1_divert: unknown proc %d\n", cs->ics.parm.dss1_io.proc);
							break;
						}

						break;

					default:
						printk(KERN_WARNING "dss1_divert unknown invoke answer %lx\n", ic->arg);
						break;
					}
					cs1 = cs; /* remember structure */
					cs = NULL;
					continue; /* abort search */
				} /* id found */
				break;

			case DSS1_CMD_INVOKE_ABORT:
				printk(KERN_WARNING "dss1_divert unhandled invoke abort\n");
				break;

			default:
				printk(KERN_WARNING "dss1_divert unknown cmd 0x%lx\n", cs->ics.arg);
				break;
			} /* switch ics.arg */
			cs = cs->next;
		} /* driver ok */
	}

	if (!cs1) {
		printk(KERN_WARNING "dss1_divert unhandled process\n");
		return (0);
	}

	if (cs1->ics.driver == -1) {
		spin_lock_irqsave(&divert_lock, flags);
		del_timer(&cs1->timer);
		if (cs1->prev)
			cs1->prev->next = cs1->next; /* forward link */
		else
			divert_head = cs1->next;
		if (cs1->next)
			cs1->next->prev = cs1->prev; /* back link */
		spin_unlock_irqrestore(&divert_lock, flags);
		kfree(cs1);
	}

	return (0);
} /* prot_stat_callback */


/***************************/
/* status callback from HL */
/***************************/
static int isdn_divert_stat_callback(isdn_ctrl *ic)
{
	struct call_struc *cs, *cs1;
	unsigned long flags;
	int retval;

	retval = -1;
	cs = divert_head; /* start of list */
	while (cs) {
		if ((ic->driver == cs->ics.driver) &&
		    (ic->arg == cs->ics.arg)) {
			switch (ic->command) {
			case ISDN_STAT_DHUP:
				sprintf(cs->info, "129 0x%lx\n", cs->divert_id);
				del_timer(&cs->timer);
				cs->ics.driver = -1;
				break;

			case ISDN_STAT_CAUSE:
				sprintf(cs->info, "130 0x%lx %s\n", cs->divert_id, ic->parm.num);
				break;

			case ISDN_STAT_REDIR:
				sprintf(cs->info, "131 0x%lx\n", cs->divert_id);
				del_timer(&cs->timer);
				cs->ics.driver = -1;
				break;

			default:
				sprintf(cs->info, "999 0x%lx 0x%x\n", cs->divert_id, (int)(ic->command));
				break;
			}
			put_info_buffer(cs->info);
			retval = 0;
		}
		cs1 = cs;
		cs = cs->next;
		if (cs1->ics.driver == -1) {
			spin_lock_irqsave(&divert_lock, flags);
			if (cs1->prev)
				cs1->prev->next = cs1->next; /* forward link */
			else
				divert_head = cs1->next;
			if (cs1->next)
				cs1->next->prev = cs1->prev; /* back link */
			spin_unlock_irqrestore(&divert_lock, flags);
			kfree(cs1);
		}
	}
	return (retval); /* not found */
} /* isdn_divert_stat_callback */


/********************/
/* callback from ll */
/********************/
int ll_callback(isdn_ctrl *ic)
{
	switch (ic->command) {
	case ISDN_STAT_ICALL:
	case ISDN_STAT_ICALLW:
		return (isdn_divert_icall(ic));
		break;

	case ISDN_STAT_PROT:
		if ((ic->arg & 0xFF) == ISDN_PTYPE_EURO) {
			if (ic->arg != DSS1_STAT_INVOKE_BRD)
				return (prot_stat_callback(ic));
			else
				return (0); /* DSS1 invoke broadcast */
		} else
			return (-1); /* protocol not euro */

	default:
		return (isdn_divert_stat_callback(ic));
	}
} /* ll_callback */
