PageRenderTime 121ms CodeModel.GetById 27ms app.highlight 79ms RepoModel.GetById 2ms app.codeStats 0ms

/drivers/isdn/gigaset/capi.c

http://github.com/mirrors/linux
C | 2533 lines | 1814 code | 236 blank | 483 comment | 286 complexity | 168e1dd58025d075e7e4d4167334ff96 MD5 | raw file

Large files files are truncated, but you can click here to view the full file

   1/*
   2 * Kernel CAPI interface for the Gigaset driver
   3 *
   4 * Copyright (c) 2009 by Tilman Schmidt <tilman@imap.cc>.
   5 *
   6 * =====================================================================
   7 *	This program is free software; you can redistribute it and/or
   8 *	modify it under the terms of the GNU General Public License as
   9 *	published by the Free Software Foundation; either version 2 of
  10 *	the License, or (at your option) any later version.
  11 * =====================================================================
  12 */
  13
  14#include "gigaset.h"
  15#include <linux/proc_fs.h>
  16#include <linux/seq_file.h>
  17#include <linux/ratelimit.h>
  18#include <linux/isdn/capilli.h>
  19#include <linux/isdn/capicmd.h>
  20#include <linux/isdn/capiutil.h>
  21#include <linux/export.h>
  22
  23/* missing from kernelcapi.h */
  24#define CapiNcpiNotSupportedByProtocol	0x0001
  25#define CapiFlagsNotSupportedByProtocol	0x0002
  26#define CapiAlertAlreadySent		0x0003
  27#define CapiFacilitySpecificFunctionNotSupported	0x3011
  28
  29/* missing from capicmd.h */
  30#define CAPI_CONNECT_IND_BASELEN	(CAPI_MSG_BASELEN + 4 + 2 + 8 * 1)
  31#define CAPI_CONNECT_ACTIVE_IND_BASELEN	(CAPI_MSG_BASELEN + 4 + 3 * 1)
  32#define CAPI_CONNECT_B3_IND_BASELEN	(CAPI_MSG_BASELEN + 4 + 1)
  33#define CAPI_CONNECT_B3_ACTIVE_IND_BASELEN	(CAPI_MSG_BASELEN + 4 + 1)
  34#define CAPI_DATA_B3_REQ_LEN64		(CAPI_MSG_BASELEN + 4 + 4 + 2 + 2 + 2 + 8)
  35#define CAPI_DATA_B3_CONF_LEN		(CAPI_MSG_BASELEN + 4 + 2 + 2)
  36#define CAPI_DISCONNECT_IND_LEN		(CAPI_MSG_BASELEN + 4 + 2)
  37#define CAPI_DISCONNECT_B3_IND_BASELEN	(CAPI_MSG_BASELEN + 4 + 2 + 1)
  38#define CAPI_FACILITY_CONF_BASELEN	(CAPI_MSG_BASELEN + 4 + 2 + 2 + 1)
  39/* most _CONF messages contain only Controller/PLCI/NCCI and Info parameters */
  40#define CAPI_STDCONF_LEN		(CAPI_MSG_BASELEN + 4 + 2)
  41
  42#define CAPI_FACILITY_HANDSET	0x0000
  43#define CAPI_FACILITY_DTMF	0x0001
  44#define CAPI_FACILITY_V42BIS	0x0002
  45#define CAPI_FACILITY_SUPPSVC	0x0003
  46#define CAPI_FACILITY_WAKEUP	0x0004
  47#define CAPI_FACILITY_LI	0x0005
  48
  49#define CAPI_SUPPSVC_GETSUPPORTED	0x0000
  50#define CAPI_SUPPSVC_LISTEN		0x0001
  51
  52/* missing from capiutil.h */
  53#define CAPIMSG_PLCI_PART(m)	CAPIMSG_U8(m, 9)
  54#define CAPIMSG_NCCI_PART(m)	CAPIMSG_U16(m, 10)
  55#define CAPIMSG_HANDLE_REQ(m)	CAPIMSG_U16(m, 18) /* DATA_B3_REQ/_IND only! */
  56#define CAPIMSG_FLAGS(m)	CAPIMSG_U16(m, 20)
  57#define CAPIMSG_SETCONTROLLER(m, contr)	capimsg_setu8(m, 8, contr)
  58#define CAPIMSG_SETPLCI_PART(m, plci)	capimsg_setu8(m, 9, plci)
  59#define CAPIMSG_SETNCCI_PART(m, ncci)	capimsg_setu16(m, 10, ncci)
  60#define CAPIMSG_SETFLAGS(m, flags)	capimsg_setu16(m, 20, flags)
  61
  62/* parameters with differing location in DATA_B3_CONF/_RESP: */
  63#define CAPIMSG_SETHANDLE_CONF(m, handle)	capimsg_setu16(m, 12, handle)
  64#define	CAPIMSG_SETINFO_CONF(m, info)		capimsg_setu16(m, 14, info)
  65
  66/* Flags (DATA_B3_REQ/_IND) */
  67#define CAPI_FLAGS_DELIVERY_CONFIRMATION	0x04
  68#define CAPI_FLAGS_RESERVED			(~0x1f)
  69
  70/* buffer sizes */
  71#define MAX_BC_OCTETS 11
  72#define MAX_HLC_OCTETS 3
  73#define MAX_NUMBER_DIGITS 20
  74#define MAX_FMT_IE_LEN 20
  75
  76/* values for bcs->apconnstate */
  77#define APCONN_NONE	0	/* inactive/listening */
  78#define APCONN_SETUP	1	/* connecting */
  79#define APCONN_ACTIVE	2	/* B channel up */
  80
  81/* registered application data structure */
  82struct gigaset_capi_appl {
  83	struct list_head ctrlist;
  84	struct gigaset_capi_appl *bcnext;
  85	u16 id;
  86	struct capi_register_params rp;
  87	u16 nextMessageNumber;
  88	u32 listenInfoMask;
  89	u32 listenCIPmask;
  90};
  91
  92/* CAPI specific controller data structure */
  93struct gigaset_capi_ctr {
  94	struct capi_ctr ctr;
  95	struct list_head appls;
  96	struct sk_buff_head sendqueue;
  97	atomic_t sendqlen;
  98	/* two _cmsg structures possibly used concurrently: */
  99	_cmsg hcmsg;	/* for message composition triggered from hardware */
 100	_cmsg acmsg;	/* for dissection of messages sent from application */
 101	u8 bc_buf[MAX_BC_OCTETS + 1];
 102	u8 hlc_buf[MAX_HLC_OCTETS + 1];
 103	u8 cgpty_buf[MAX_NUMBER_DIGITS + 3];
 104	u8 cdpty_buf[MAX_NUMBER_DIGITS + 2];
 105};
 106
 107/* CIP Value table (from CAPI 2.0 standard, ch. 6.1) */
 108static struct {
 109	u8 *bc;
 110	u8 *hlc;
 111} cip2bchlc[] = {
 112	[1] = { "8090A3", NULL },	/* Speech (A-law) */
 113	[2] = { "8890", NULL },		/* Unrestricted digital information */
 114	[3] = { "8990", NULL },		/* Restricted digital information */
 115	[4] = { "9090A3", NULL },	/* 3,1 kHz audio (A-law) */
 116	[5] = { "9190", NULL },		/* 7 kHz audio */
 117	[6] = { "9890", NULL },		/* Video */
 118	[7] = { "88C0C6E6", NULL },	/* Packet mode */
 119	[8] = { "8890218F", NULL },	/* 56 kbit/s rate adaptation */
 120	[9] = { "9190A5", NULL },	/* Unrestricted digital information
 121					 * with tones/announcements */
 122	[16] = { "8090A3", "9181" },	/* Telephony */
 123	[17] = { "9090A3", "9184" },	/* Group 2/3 facsimile */
 124	[18] = { "8890", "91A1" },	/* Group 4 facsimile Class 1 */
 125	[19] = { "8890", "91A4" },	/* Teletex service basic and mixed mode
 126					 * and Group 4 facsimile service
 127					 * Classes II and III */
 128	[20] = { "8890", "91A8" },	/* Teletex service basic and
 129					 * processable mode */
 130	[21] = { "8890", "91B1" },	/* Teletex service basic mode */
 131	[22] = { "8890", "91B2" },	/* International interworking for
 132					 * Videotex */
 133	[23] = { "8890", "91B5" },	/* Telex */
 134	[24] = { "8890", "91B8" },	/* Message Handling Systems
 135					 * in accordance with X.400 */
 136	[25] = { "8890", "91C1" },	/* OSI application
 137					 * in accordance with X.200 */
 138	[26] = { "9190A5", "9181" },	/* 7 kHz telephony */
 139	[27] = { "9190A5", "916001" },	/* Video telephony, first connection */
 140	[28] = { "8890", "916002" },	/* Video telephony, second connection */
 141};
 142
 143/*
 144 * helper functions
 145 * ================
 146 */
 147
 148/*
 149 * emit unsupported parameter warning
 150 */
 151static inline void ignore_cstruct_param(struct cardstate *cs, _cstruct param,
 152					char *msgname, char *paramname)
 153{
 154	if (param && *param)
 155		dev_warn(cs->dev, "%s: ignoring unsupported parameter: %s\n",
 156			 msgname, paramname);
 157}
 158
 159/*
 160 * convert an IE from Gigaset hex string to ETSI binary representation
 161 * including length byte
 162 * return value: result length, -1 on error
 163 */
 164static int encode_ie(char *in, u8 *out, int maxlen)
 165{
 166	int l = 0;
 167	while (*in) {
 168		if (!isxdigit(in[0]) || !isxdigit(in[1]) || l >= maxlen)
 169			return -1;
 170		out[++l] = (hex_to_bin(in[0]) << 4) + hex_to_bin(in[1]);
 171		in += 2;
 172	}
 173	out[0] = l;
 174	return l;
 175}
 176
 177/*
 178 * convert an IE from ETSI binary representation including length byte
 179 * to Gigaset hex string
 180 */
 181static void decode_ie(u8 *in, char *out)
 182{
 183	int i = *in;
 184	while (i-- > 0) {
 185		/* ToDo: conversion to upper case necessary? */
 186		*out++ = toupper(hex_asc_hi(*++in));
 187		*out++ = toupper(hex_asc_lo(*in));
 188	}
 189}
 190
 191/*
 192 * retrieve application data structure for an application ID
 193 */
 194static inline struct gigaset_capi_appl *
 195get_appl(struct gigaset_capi_ctr *iif, u16 appl)
 196{
 197	struct gigaset_capi_appl *ap;
 198
 199	list_for_each_entry(ap, &iif->appls, ctrlist)
 200		if (ap->id == appl)
 201			return ap;
 202	return NULL;
 203}
 204
 205/*
 206 * dump CAPI message to kernel messages for debugging
 207 */
 208static inline void dump_cmsg(enum debuglevel level, const char *tag, _cmsg *p)
 209{
 210#ifdef CONFIG_GIGASET_DEBUG
 211	/* dump at most 20 messages in 20 secs */
 212	static DEFINE_RATELIMIT_STATE(msg_dump_ratelimit, 20 * HZ, 20);
 213	_cdebbuf *cdb;
 214
 215	if (!(gigaset_debuglevel & level))
 216		return;
 217	if (!___ratelimit(&msg_dump_ratelimit, tag))
 218		return;
 219
 220	cdb = capi_cmsg2str(p);
 221	if (cdb) {
 222		gig_dbg(level, "%s: [%d] %s", tag, p->ApplId, cdb->buf);
 223		cdebbuf_free(cdb);
 224	} else {
 225		gig_dbg(level, "%s: [%d] %s", tag, p->ApplId,
 226			capi_cmd2str(p->Command, p->Subcommand));
 227	}
 228#endif
 229}
 230
 231static inline void dump_rawmsg(enum debuglevel level, const char *tag,
 232			       unsigned char *data)
 233{
 234#ifdef CONFIG_GIGASET_DEBUG
 235	char *dbgline;
 236	int i, l;
 237
 238	if (!(gigaset_debuglevel & level))
 239		return;
 240
 241	l = CAPIMSG_LEN(data);
 242	if (l < 12) {
 243		gig_dbg(level, "%s: ??? LEN=%04d", tag, l);
 244		return;
 245	}
 246	gig_dbg(level, "%s: 0x%02x:0x%02x: ID=%03d #0x%04x LEN=%04d NCCI=0x%x",
 247		tag, CAPIMSG_COMMAND(data), CAPIMSG_SUBCOMMAND(data),
 248		CAPIMSG_APPID(data), CAPIMSG_MSGID(data), l,
 249		CAPIMSG_CONTROL(data));
 250	l -= 12;
 251	if (l <= 0)
 252		return;
 253	if (l > 64)
 254		l = 64; /* arbitrary limit */
 255	dbgline = kmalloc(3 * l, GFP_ATOMIC);
 256	if (!dbgline)
 257		return;
 258	for (i = 0; i < l; i++) {
 259		dbgline[3 * i] = hex_asc_hi(data[12 + i]);
 260		dbgline[3 * i + 1] = hex_asc_lo(data[12 + i]);
 261		dbgline[3 * i + 2] = ' ';
 262	}
 263	dbgline[3 * l - 1] = '\0';
 264	gig_dbg(level, "  %s", dbgline);
 265	kfree(dbgline);
 266	if (CAPIMSG_COMMAND(data) == CAPI_DATA_B3 &&
 267	    (CAPIMSG_SUBCOMMAND(data) == CAPI_REQ ||
 268	     CAPIMSG_SUBCOMMAND(data) == CAPI_IND)) {
 269		l = CAPIMSG_DATALEN(data);
 270		gig_dbg(level, "   DataLength=%d", l);
 271		if (l <= 0 || !(gigaset_debuglevel & DEBUG_LLDATA))
 272			return;
 273		if (l > 64)
 274			l = 64; /* arbitrary limit */
 275		dbgline = kmalloc(3 * l, GFP_ATOMIC);
 276		if (!dbgline)
 277			return;
 278		data += CAPIMSG_LEN(data);
 279		for (i = 0; i < l; i++) {
 280			dbgline[3 * i] = hex_asc_hi(data[i]);
 281			dbgline[3 * i + 1] = hex_asc_lo(data[i]);
 282			dbgline[3 * i + 2] = ' ';
 283		}
 284		dbgline[3 * l - 1] = '\0';
 285		gig_dbg(level, "  %s", dbgline);
 286		kfree(dbgline);
 287	}
 288#endif
 289}
 290
 291/*
 292 * format CAPI IE as string
 293 */
 294
 295#ifdef CONFIG_GIGASET_DEBUG
 296static const char *format_ie(const char *ie)
 297{
 298	static char result[3 * MAX_FMT_IE_LEN];
 299	int len, count;
 300	char *pout = result;
 301
 302	if (!ie)
 303		return "NULL";
 304
 305	count = len = ie[0];
 306	if (count > MAX_FMT_IE_LEN)
 307		count = MAX_FMT_IE_LEN - 1;
 308	while (count--) {
 309		*pout++ = hex_asc_hi(*++ie);
 310		*pout++ = hex_asc_lo(*ie);
 311		*pout++ = ' ';
 312	}
 313	if (len > MAX_FMT_IE_LEN) {
 314		*pout++ = '.';
 315		*pout++ = '.';
 316		*pout++ = '.';
 317	}
 318	*--pout = 0;
 319	return result;
 320}
 321#endif
 322
 323/*
 324 * emit DATA_B3_CONF message
 325 */
 326static void send_data_b3_conf(struct cardstate *cs, struct capi_ctr *ctr,
 327			      u16 appl, u16 msgid, int channel,
 328			      u16 handle, u16 info)
 329{
 330	struct sk_buff *cskb;
 331	u8 *msg;
 332
 333	cskb = alloc_skb(CAPI_DATA_B3_CONF_LEN, GFP_ATOMIC);
 334	if (!cskb) {
 335		dev_err(cs->dev, "%s: out of memory\n", __func__);
 336		return;
 337	}
 338	/* frequent message, avoid _cmsg overhead */
 339	msg = __skb_put(cskb, CAPI_DATA_B3_CONF_LEN);
 340	CAPIMSG_SETLEN(msg, CAPI_DATA_B3_CONF_LEN);
 341	CAPIMSG_SETAPPID(msg, appl);
 342	CAPIMSG_SETCOMMAND(msg, CAPI_DATA_B3);
 343	CAPIMSG_SETSUBCOMMAND(msg,  CAPI_CONF);
 344	CAPIMSG_SETMSGID(msg, msgid);
 345	CAPIMSG_SETCONTROLLER(msg, ctr->cnr);
 346	CAPIMSG_SETPLCI_PART(msg, channel);
 347	CAPIMSG_SETNCCI_PART(msg, 1);
 348	CAPIMSG_SETHANDLE_CONF(msg, handle);
 349	CAPIMSG_SETINFO_CONF(msg, info);
 350
 351	/* emit message */
 352	dump_rawmsg(DEBUG_MCMD, __func__, msg);
 353	capi_ctr_handle_message(ctr, appl, cskb);
 354}
 355
 356
 357/*
 358 * driver interface functions
 359 * ==========================
 360 */
 361
 362/**
 363 * gigaset_skb_sent() - acknowledge transmission of outgoing skb
 364 * @bcs:	B channel descriptor structure.
 365 * @skb:	sent data.
 366 *
 367 * Called by hardware module {bas,ser,usb}_gigaset when the data in a
 368 * skb has been successfully sent, for signalling completion to the LL.
 369 */
 370void gigaset_skb_sent(struct bc_state *bcs, struct sk_buff *dskb)
 371{
 372	struct cardstate *cs = bcs->cs;
 373	struct gigaset_capi_ctr *iif = cs->iif;
 374	struct gigaset_capi_appl *ap = bcs->ap;
 375	unsigned char *req = skb_mac_header(dskb);
 376	u16 flags;
 377
 378	/* update statistics */
 379	++bcs->trans_up;
 380
 381	if (!ap) {
 382		gig_dbg(DEBUG_MCMD, "%s: application gone", __func__);
 383		return;
 384	}
 385
 386	/* don't send further B3 messages if disconnected */
 387	if (bcs->apconnstate < APCONN_ACTIVE) {
 388		gig_dbg(DEBUG_MCMD, "%s: disconnected", __func__);
 389		return;
 390	}
 391
 392	/*
 393	 * send DATA_B3_CONF if "delivery confirmation" bit was set in request;
 394	 * otherwise it has already been sent by do_data_b3_req()
 395	 */
 396	flags = CAPIMSG_FLAGS(req);
 397	if (flags & CAPI_FLAGS_DELIVERY_CONFIRMATION)
 398		send_data_b3_conf(cs, &iif->ctr, ap->id, CAPIMSG_MSGID(req),
 399				  bcs->channel + 1, CAPIMSG_HANDLE_REQ(req),
 400				  (flags & ~CAPI_FLAGS_DELIVERY_CONFIRMATION) ?
 401				  CapiFlagsNotSupportedByProtocol :
 402				  CAPI_NOERROR);
 403}
 404EXPORT_SYMBOL_GPL(gigaset_skb_sent);
 405
 406/**
 407 * gigaset_skb_rcvd() - pass received skb to LL
 408 * @bcs:	B channel descriptor structure.
 409 * @skb:	received data.
 410 *
 411 * Called by hardware module {bas,ser,usb}_gigaset when user data has
 412 * been successfully received, for passing to the LL.
 413 * Warning: skb must not be accessed anymore!
 414 */
 415void gigaset_skb_rcvd(struct bc_state *bcs, struct sk_buff *skb)
 416{
 417	struct cardstate *cs = bcs->cs;
 418	struct gigaset_capi_ctr *iif = cs->iif;
 419	struct gigaset_capi_appl *ap = bcs->ap;
 420	int len = skb->len;
 421
 422	/* update statistics */
 423	bcs->trans_down++;
 424
 425	if (!ap) {
 426		gig_dbg(DEBUG_MCMD, "%s: application gone", __func__);
 427		dev_kfree_skb_any(skb);
 428		return;
 429	}
 430
 431	/* don't send further B3 messages if disconnected */
 432	if (bcs->apconnstate < APCONN_ACTIVE) {
 433		gig_dbg(DEBUG_MCMD, "%s: disconnected", __func__);
 434		dev_kfree_skb_any(skb);
 435		return;
 436	}
 437
 438	/*
 439	 * prepend DATA_B3_IND message to payload
 440	 * Parameters: NCCI = 1, all others 0/unused
 441	 * frequent message, avoid _cmsg overhead
 442	 */
 443	skb_push(skb, CAPI_DATA_B3_REQ_LEN);
 444	CAPIMSG_SETLEN(skb->data, CAPI_DATA_B3_REQ_LEN);
 445	CAPIMSG_SETAPPID(skb->data, ap->id);
 446	CAPIMSG_SETCOMMAND(skb->data, CAPI_DATA_B3);
 447	CAPIMSG_SETSUBCOMMAND(skb->data,  CAPI_IND);
 448	CAPIMSG_SETMSGID(skb->data, ap->nextMessageNumber++);
 449	CAPIMSG_SETCONTROLLER(skb->data, iif->ctr.cnr);
 450	CAPIMSG_SETPLCI_PART(skb->data, bcs->channel + 1);
 451	CAPIMSG_SETNCCI_PART(skb->data, 1);
 452	/* Data parameter not used */
 453	CAPIMSG_SETDATALEN(skb->data, len);
 454	/* Data handle parameter not used */
 455	CAPIMSG_SETFLAGS(skb->data, 0);
 456	/* Data64 parameter not present */
 457
 458	/* emit message */
 459	dump_rawmsg(DEBUG_MCMD, __func__, skb->data);
 460	capi_ctr_handle_message(&iif->ctr, ap->id, skb);
 461}
 462EXPORT_SYMBOL_GPL(gigaset_skb_rcvd);
 463
 464/**
 465 * gigaset_isdn_rcv_err() - signal receive error
 466 * @bcs:	B channel descriptor structure.
 467 *
 468 * Called by hardware module {bas,ser,usb}_gigaset when a receive error
 469 * has occurred, for signalling to the LL.
 470 */
 471void gigaset_isdn_rcv_err(struct bc_state *bcs)
 472{
 473	/* if currently ignoring packets, just count down */
 474	if (bcs->ignore) {
 475		bcs->ignore--;
 476		return;
 477	}
 478
 479	/* update statistics */
 480	bcs->corrupted++;
 481
 482	/* ToDo: signal error -> LL */
 483}
 484EXPORT_SYMBOL_GPL(gigaset_isdn_rcv_err);
 485
 486/**
 487 * gigaset_isdn_icall() - signal incoming call
 488 * @at_state:	connection state structure.
 489 *
 490 * Called by main module at tasklet level to notify the LL that an incoming
 491 * call has been received. @at_state contains the parameters of the call.
 492 *
 493 * Return value: call disposition (ICALL_*)
 494 */
 495int gigaset_isdn_icall(struct at_state_t *at_state)
 496{
 497	struct cardstate *cs = at_state->cs;
 498	struct bc_state *bcs = at_state->bcs;
 499	struct gigaset_capi_ctr *iif = cs->iif;
 500	struct gigaset_capi_appl *ap;
 501	u32 actCIPmask;
 502	struct sk_buff *skb;
 503	unsigned int msgsize;
 504	unsigned long flags;
 505	int i;
 506
 507	/*
 508	 * ToDo: signal calls without a free B channel, too
 509	 * (requires a u8 handle for the at_state structure that can
 510	 * be stored in the PLCI and used in the CONNECT_RESP message
 511	 * handler to retrieve it)
 512	 */
 513	if (!bcs)
 514		return ICALL_IGNORE;
 515
 516	/* prepare CONNECT_IND message, using B channel number as PLCI */
 517	capi_cmsg_header(&iif->hcmsg, 0, CAPI_CONNECT, CAPI_IND, 0,
 518			 iif->ctr.cnr | ((bcs->channel + 1) << 8));
 519
 520	/* minimum size, all structs empty */
 521	msgsize = CAPI_CONNECT_IND_BASELEN;
 522
 523	/* Bearer Capability (mandatory) */
 524	if (at_state->str_var[STR_ZBC]) {
 525		/* pass on BC from Gigaset */
 526		if (encode_ie(at_state->str_var[STR_ZBC], iif->bc_buf,
 527			      MAX_BC_OCTETS) < 0) {
 528			dev_warn(cs->dev, "RING ignored - bad BC %s\n",
 529				 at_state->str_var[STR_ZBC]);
 530			return ICALL_IGNORE;
 531		}
 532
 533		/* look up corresponding CIP value */
 534		iif->hcmsg.CIPValue = 0;	/* default if nothing found */
 535		for (i = 0; i < ARRAY_SIZE(cip2bchlc); i++)
 536			if (cip2bchlc[i].bc != NULL &&
 537			    cip2bchlc[i].hlc == NULL &&
 538			    !strcmp(cip2bchlc[i].bc,
 539				    at_state->str_var[STR_ZBC])) {
 540				iif->hcmsg.CIPValue = i;
 541				break;
 542			}
 543	} else {
 544		/* no BC (internal call): assume CIP 1 (speech, A-law) */
 545		iif->hcmsg.CIPValue = 1;
 546		encode_ie(cip2bchlc[1].bc, iif->bc_buf, MAX_BC_OCTETS);
 547	}
 548	iif->hcmsg.BC = iif->bc_buf;
 549	msgsize += iif->hcmsg.BC[0];
 550
 551	/* High Layer Compatibility (optional) */
 552	if (at_state->str_var[STR_ZHLC]) {
 553		/* pass on HLC from Gigaset */
 554		if (encode_ie(at_state->str_var[STR_ZHLC], iif->hlc_buf,
 555			      MAX_HLC_OCTETS) < 0) {
 556			dev_warn(cs->dev, "RING ignored - bad HLC %s\n",
 557				 at_state->str_var[STR_ZHLC]);
 558			return ICALL_IGNORE;
 559		}
 560		iif->hcmsg.HLC = iif->hlc_buf;
 561		msgsize += iif->hcmsg.HLC[0];
 562
 563		/* look up corresponding CIP value */
 564		/* keep BC based CIP value if none found */
 565		if (at_state->str_var[STR_ZBC])
 566			for (i = 0; i < ARRAY_SIZE(cip2bchlc); i++)
 567				if (cip2bchlc[i].hlc != NULL &&
 568				    !strcmp(cip2bchlc[i].hlc,
 569					    at_state->str_var[STR_ZHLC]) &&
 570				    !strcmp(cip2bchlc[i].bc,
 571					    at_state->str_var[STR_ZBC])) {
 572					iif->hcmsg.CIPValue = i;
 573					break;
 574				}
 575	}
 576
 577	/* Called Party Number (optional) */
 578	if (at_state->str_var[STR_ZCPN]) {
 579		i = strlen(at_state->str_var[STR_ZCPN]);
 580		if (i > MAX_NUMBER_DIGITS) {
 581			dev_warn(cs->dev, "RING ignored - bad number %s\n",
 582				 at_state->str_var[STR_ZBC]);
 583			return ICALL_IGNORE;
 584		}
 585		iif->cdpty_buf[0] = i + 1;
 586		iif->cdpty_buf[1] = 0x80; /* type / numbering plan unknown */
 587		memcpy(iif->cdpty_buf + 2, at_state->str_var[STR_ZCPN], i);
 588		iif->hcmsg.CalledPartyNumber = iif->cdpty_buf;
 589		msgsize += iif->hcmsg.CalledPartyNumber[0];
 590	}
 591
 592	/* Calling Party Number (optional) */
 593	if (at_state->str_var[STR_NMBR]) {
 594		i = strlen(at_state->str_var[STR_NMBR]);
 595		if (i > MAX_NUMBER_DIGITS) {
 596			dev_warn(cs->dev, "RING ignored - bad number %s\n",
 597				 at_state->str_var[STR_ZBC]);
 598			return ICALL_IGNORE;
 599		}
 600		iif->cgpty_buf[0] = i + 2;
 601		iif->cgpty_buf[1] = 0x00; /* type / numbering plan unknown */
 602		iif->cgpty_buf[2] = 0x80; /* pres. allowed, not screened */
 603		memcpy(iif->cgpty_buf + 3, at_state->str_var[STR_NMBR], i);
 604		iif->hcmsg.CallingPartyNumber = iif->cgpty_buf;
 605		msgsize += iif->hcmsg.CallingPartyNumber[0];
 606	}
 607
 608	/* remaining parameters (not supported, always left NULL):
 609	 * - CalledPartySubaddress
 610	 * - CallingPartySubaddress
 611	 * - AdditionalInfo
 612	 *   - BChannelinformation
 613	 *   - Keypadfacility
 614	 *   - Useruserdata
 615	 *   - Facilitydataarray
 616	 */
 617
 618	gig_dbg(DEBUG_CMD, "icall: PLCI %x CIP %d BC %s",
 619		iif->hcmsg.adr.adrPLCI, iif->hcmsg.CIPValue,
 620		format_ie(iif->hcmsg.BC));
 621	gig_dbg(DEBUG_CMD, "icall: HLC %s",
 622		format_ie(iif->hcmsg.HLC));
 623	gig_dbg(DEBUG_CMD, "icall: CgPty %s",
 624		format_ie(iif->hcmsg.CallingPartyNumber));
 625	gig_dbg(DEBUG_CMD, "icall: CdPty %s",
 626		format_ie(iif->hcmsg.CalledPartyNumber));
 627
 628	/* scan application list for matching listeners */
 629	spin_lock_irqsave(&bcs->aplock, flags);
 630	if (bcs->ap != NULL || bcs->apconnstate != APCONN_NONE) {
 631		dev_warn(cs->dev, "%s: channel not properly cleared (%p/%d)\n",
 632			 __func__, bcs->ap, bcs->apconnstate);
 633		bcs->ap = NULL;
 634		bcs->apconnstate = APCONN_NONE;
 635	}
 636	spin_unlock_irqrestore(&bcs->aplock, flags);
 637	actCIPmask = 1 | (1 << iif->hcmsg.CIPValue);
 638	list_for_each_entry(ap, &iif->appls, ctrlist)
 639		if (actCIPmask & ap->listenCIPmask) {
 640			/* build CONNECT_IND message for this application */
 641			iif->hcmsg.ApplId = ap->id;
 642			iif->hcmsg.Messagenumber = ap->nextMessageNumber++;
 643
 644			skb = alloc_skb(msgsize, GFP_ATOMIC);
 645			if (!skb) {
 646				dev_err(cs->dev, "%s: out of memory\n",
 647					__func__);
 648				break;
 649			}
 650			if (capi_cmsg2message(&iif->hcmsg,
 651					      __skb_put(skb, msgsize))) {
 652				dev_err(cs->dev, "%s: message parser failure\n",
 653					__func__);
 654				dev_kfree_skb_any(skb);
 655				break;
 656			}
 657			dump_cmsg(DEBUG_CMD, __func__, &iif->hcmsg);
 658
 659			/* add to listeners on this B channel, update state */
 660			spin_lock_irqsave(&bcs->aplock, flags);
 661			ap->bcnext = bcs->ap;
 662			bcs->ap = ap;
 663			bcs->chstate |= CHS_NOTIFY_LL;
 664			bcs->apconnstate = APCONN_SETUP;
 665			spin_unlock_irqrestore(&bcs->aplock, flags);
 666
 667			/* emit message */
 668			capi_ctr_handle_message(&iif->ctr, ap->id, skb);
 669		}
 670
 671	/*
 672	 * Return "accept" if any listeners.
 673	 * Gigaset will send ALERTING.
 674	 * There doesn't seem to be a way to avoid this.
 675	 */
 676	return bcs->ap ? ICALL_ACCEPT : ICALL_IGNORE;
 677}
 678
 679/*
 680 * send a DISCONNECT_IND message to an application
 681 * does not sleep, clobbers the controller's hcmsg structure
 682 */
 683static void send_disconnect_ind(struct bc_state *bcs,
 684				struct gigaset_capi_appl *ap, u16 reason)
 685{
 686	struct cardstate *cs = bcs->cs;
 687	struct gigaset_capi_ctr *iif = cs->iif;
 688	struct sk_buff *skb;
 689
 690	if (bcs->apconnstate == APCONN_NONE)
 691		return;
 692
 693	capi_cmsg_header(&iif->hcmsg, ap->id, CAPI_DISCONNECT, CAPI_IND,
 694			 ap->nextMessageNumber++,
 695			 iif->ctr.cnr | ((bcs->channel + 1) << 8));
 696	iif->hcmsg.Reason = reason;
 697	skb = alloc_skb(CAPI_DISCONNECT_IND_LEN, GFP_ATOMIC);
 698	if (!skb) {
 699		dev_err(cs->dev, "%s: out of memory\n", __func__);
 700		return;
 701	}
 702	if (capi_cmsg2message(&iif->hcmsg,
 703			      __skb_put(skb, CAPI_DISCONNECT_IND_LEN))) {
 704		dev_err(cs->dev, "%s: message parser failure\n", __func__);
 705		dev_kfree_skb_any(skb);
 706		return;
 707	}
 708	dump_cmsg(DEBUG_CMD, __func__, &iif->hcmsg);
 709	capi_ctr_handle_message(&iif->ctr, ap->id, skb);
 710}
 711
 712/*
 713 * send a DISCONNECT_B3_IND message to an application
 714 * Parameters: NCCI = 1, NCPI empty, Reason_B3 = 0
 715 * does not sleep, clobbers the controller's hcmsg structure
 716 */
 717static void send_disconnect_b3_ind(struct bc_state *bcs,
 718				   struct gigaset_capi_appl *ap)
 719{
 720	struct cardstate *cs = bcs->cs;
 721	struct gigaset_capi_ctr *iif = cs->iif;
 722	struct sk_buff *skb;
 723
 724	/* nothing to do if no logical connection active */
 725	if (bcs->apconnstate < APCONN_ACTIVE)
 726		return;
 727	bcs->apconnstate = APCONN_SETUP;
 728
 729	capi_cmsg_header(&iif->hcmsg, ap->id, CAPI_DISCONNECT_B3, CAPI_IND,
 730			 ap->nextMessageNumber++,
 731			 iif->ctr.cnr | ((bcs->channel + 1) << 8) | (1 << 16));
 732	skb = alloc_skb(CAPI_DISCONNECT_B3_IND_BASELEN, GFP_ATOMIC);
 733	if (!skb) {
 734		dev_err(cs->dev, "%s: out of memory\n", __func__);
 735		return;
 736	}
 737	if (capi_cmsg2message(&iif->hcmsg,
 738			  __skb_put(skb, CAPI_DISCONNECT_B3_IND_BASELEN))) {
 739		dev_err(cs->dev, "%s: message parser failure\n", __func__);
 740		dev_kfree_skb_any(skb);
 741		return;
 742	}
 743	dump_cmsg(DEBUG_CMD, __func__, &iif->hcmsg);
 744	capi_ctr_handle_message(&iif->ctr, ap->id, skb);
 745}
 746
 747/**
 748 * gigaset_isdn_connD() - signal D channel connect
 749 * @bcs:	B channel descriptor structure.
 750 *
 751 * Called by main module at tasklet level to notify the LL that the D channel
 752 * connection has been established.
 753 */
 754void gigaset_isdn_connD(struct bc_state *bcs)
 755{
 756	struct cardstate *cs = bcs->cs;
 757	struct gigaset_capi_ctr *iif = cs->iif;
 758	struct gigaset_capi_appl *ap;
 759	struct sk_buff *skb;
 760	unsigned int msgsize;
 761	unsigned long flags;
 762
 763	spin_lock_irqsave(&bcs->aplock, flags);
 764	ap = bcs->ap;
 765	if (!ap) {
 766		spin_unlock_irqrestore(&bcs->aplock, flags);
 767		gig_dbg(DEBUG_CMD, "%s: application gone", __func__);
 768		return;
 769	}
 770	if (bcs->apconnstate == APCONN_NONE) {
 771		spin_unlock_irqrestore(&bcs->aplock, flags);
 772		dev_warn(cs->dev, "%s: application %u not connected\n",
 773			 __func__, ap->id);
 774		return;
 775	}
 776	spin_unlock_irqrestore(&bcs->aplock, flags);
 777	while (ap->bcnext) {
 778		/* this should never happen */
 779		dev_warn(cs->dev, "%s: dropping extra application %u\n",
 780			 __func__, ap->bcnext->id);
 781		send_disconnect_ind(bcs, ap->bcnext,
 782				    CapiCallGivenToOtherApplication);
 783		ap->bcnext = ap->bcnext->bcnext;
 784	}
 785
 786	/* prepare CONNECT_ACTIVE_IND message
 787	 * Note: LLC not supported by device
 788	 */
 789	capi_cmsg_header(&iif->hcmsg, ap->id, CAPI_CONNECT_ACTIVE, CAPI_IND,
 790			 ap->nextMessageNumber++,
 791			 iif->ctr.cnr | ((bcs->channel + 1) << 8));
 792
 793	/* minimum size, all structs empty */
 794	msgsize = CAPI_CONNECT_ACTIVE_IND_BASELEN;
 795
 796	/* ToDo: set parameter: Connected number
 797	 * (requires ev-layer state machine extension to collect
 798	 * ZCON device reply)
 799	 */
 800
 801	/* build and emit CONNECT_ACTIVE_IND message */
 802	skb = alloc_skb(msgsize, GFP_ATOMIC);
 803	if (!skb) {
 804		dev_err(cs->dev, "%s: out of memory\n", __func__);
 805		return;
 806	}
 807	if (capi_cmsg2message(&iif->hcmsg, __skb_put(skb, msgsize))) {
 808		dev_err(cs->dev, "%s: message parser failure\n", __func__);
 809		dev_kfree_skb_any(skb);
 810		return;
 811	}
 812	dump_cmsg(DEBUG_CMD, __func__, &iif->hcmsg);
 813	capi_ctr_handle_message(&iif->ctr, ap->id, skb);
 814}
 815
 816/**
 817 * gigaset_isdn_hupD() - signal D channel hangup
 818 * @bcs:	B channel descriptor structure.
 819 *
 820 * Called by main module at tasklet level to notify the LL that the D channel
 821 * connection has been shut down.
 822 */
 823void gigaset_isdn_hupD(struct bc_state *bcs)
 824{
 825	struct gigaset_capi_appl *ap;
 826	unsigned long flags;
 827
 828	/*
 829	 * ToDo: pass on reason code reported by device
 830	 * (requires ev-layer state machine extension to collect
 831	 * ZCAU device reply)
 832	 */
 833	spin_lock_irqsave(&bcs->aplock, flags);
 834	while (bcs->ap != NULL) {
 835		ap = bcs->ap;
 836		bcs->ap = ap->bcnext;
 837		spin_unlock_irqrestore(&bcs->aplock, flags);
 838		send_disconnect_b3_ind(bcs, ap);
 839		send_disconnect_ind(bcs, ap, 0);
 840		spin_lock_irqsave(&bcs->aplock, flags);
 841	}
 842	bcs->apconnstate = APCONN_NONE;
 843	spin_unlock_irqrestore(&bcs->aplock, flags);
 844}
 845
 846/**
 847 * gigaset_isdn_connB() - signal B channel connect
 848 * @bcs:	B channel descriptor structure.
 849 *
 850 * Called by main module at tasklet level to notify the LL that the B channel
 851 * connection has been established.
 852 */
 853void gigaset_isdn_connB(struct bc_state *bcs)
 854{
 855	struct cardstate *cs = bcs->cs;
 856	struct gigaset_capi_ctr *iif = cs->iif;
 857	struct gigaset_capi_appl *ap;
 858	struct sk_buff *skb;
 859	unsigned long flags;
 860	unsigned int msgsize;
 861	u8 command;
 862
 863	spin_lock_irqsave(&bcs->aplock, flags);
 864	ap = bcs->ap;
 865	if (!ap) {
 866		spin_unlock_irqrestore(&bcs->aplock, flags);
 867		gig_dbg(DEBUG_CMD, "%s: application gone", __func__);
 868		return;
 869	}
 870	if (!bcs->apconnstate) {
 871		spin_unlock_irqrestore(&bcs->aplock, flags);
 872		dev_warn(cs->dev, "%s: application %u not connected\n",
 873			 __func__, ap->id);
 874		return;
 875	}
 876
 877	/*
 878	 * emit CONNECT_B3_ACTIVE_IND if we already got CONNECT_B3_REQ;
 879	 * otherwise we have to emit CONNECT_B3_IND first, and follow up with
 880	 * CONNECT_B3_ACTIVE_IND in reply to CONNECT_B3_RESP
 881	 * Parameters in both cases always: NCCI = 1, NCPI empty
 882	 */
 883	if (bcs->apconnstate >= APCONN_ACTIVE) {
 884		command = CAPI_CONNECT_B3_ACTIVE;
 885		msgsize = CAPI_CONNECT_B3_ACTIVE_IND_BASELEN;
 886	} else {
 887		command = CAPI_CONNECT_B3;
 888		msgsize = CAPI_CONNECT_B3_IND_BASELEN;
 889	}
 890	bcs->apconnstate = APCONN_ACTIVE;
 891
 892	spin_unlock_irqrestore(&bcs->aplock, flags);
 893
 894	while (ap->bcnext) {
 895		/* this should never happen */
 896		dev_warn(cs->dev, "%s: dropping extra application %u\n",
 897			 __func__, ap->bcnext->id);
 898		send_disconnect_ind(bcs, ap->bcnext,
 899				    CapiCallGivenToOtherApplication);
 900		ap->bcnext = ap->bcnext->bcnext;
 901	}
 902
 903	capi_cmsg_header(&iif->hcmsg, ap->id, command, CAPI_IND,
 904			 ap->nextMessageNumber++,
 905			 iif->ctr.cnr | ((bcs->channel + 1) << 8) | (1 << 16));
 906	skb = alloc_skb(msgsize, GFP_ATOMIC);
 907	if (!skb) {
 908		dev_err(cs->dev, "%s: out of memory\n", __func__);
 909		return;
 910	}
 911	if (capi_cmsg2message(&iif->hcmsg, __skb_put(skb, msgsize))) {
 912		dev_err(cs->dev, "%s: message parser failure\n", __func__);
 913		dev_kfree_skb_any(skb);
 914		return;
 915	}
 916	dump_cmsg(DEBUG_CMD, __func__, &iif->hcmsg);
 917	capi_ctr_handle_message(&iif->ctr, ap->id, skb);
 918}
 919
 920/**
 921 * gigaset_isdn_hupB() - signal B channel hangup
 922 * @bcs:	B channel descriptor structure.
 923 *
 924 * Called by main module to notify the LL that the B channel connection has
 925 * been shut down.
 926 */
 927void gigaset_isdn_hupB(struct bc_state *bcs)
 928{
 929	struct gigaset_capi_appl *ap = bcs->ap;
 930
 931	/* ToDo: assure order of DISCONNECT_B3_IND and DISCONNECT_IND ? */
 932
 933	if (!ap) {
 934		gig_dbg(DEBUG_CMD, "%s: application gone", __func__);
 935		return;
 936	}
 937
 938	send_disconnect_b3_ind(bcs, ap);
 939}
 940
 941/**
 942 * gigaset_isdn_start() - signal device availability
 943 * @cs:		device descriptor structure.
 944 *
 945 * Called by main module to notify the LL that the device is available for
 946 * use.
 947 */
 948void gigaset_isdn_start(struct cardstate *cs)
 949{
 950	struct gigaset_capi_ctr *iif = cs->iif;
 951
 952	/* fill profile data: manufacturer name */
 953	strcpy(iif->ctr.manu, "Siemens");
 954	/* CAPI and device version */
 955	iif->ctr.version.majorversion = 2;		/* CAPI 2.0 */
 956	iif->ctr.version.minorversion = 0;
 957	/* ToDo: check/assert cs->gotfwver? */
 958	iif->ctr.version.majormanuversion = cs->fwver[0];
 959	iif->ctr.version.minormanuversion = cs->fwver[1];
 960	/* number of B channels supported */
 961	iif->ctr.profile.nbchannel = cs->channels;
 962	/* global options: internal controller, supplementary services */
 963	iif->ctr.profile.goptions = 0x11;
 964	/* B1 protocols: 64 kbit/s HDLC or transparent */
 965	iif->ctr.profile.support1 =  0x03;
 966	/* B2 protocols: transparent only */
 967	/* ToDo: X.75 SLP ? */
 968	iif->ctr.profile.support2 =  0x02;
 969	/* B3 protocols: transparent only */
 970	iif->ctr.profile.support3 =  0x01;
 971	/* no serial number */
 972	strcpy(iif->ctr.serial, "0");
 973	capi_ctr_ready(&iif->ctr);
 974}
 975
 976/**
 977 * gigaset_isdn_stop() - signal device unavailability
 978 * @cs:		device descriptor structure.
 979 *
 980 * Called by main module to notify the LL that the device is no longer
 981 * available for use.
 982 */
 983void gigaset_isdn_stop(struct cardstate *cs)
 984{
 985	struct gigaset_capi_ctr *iif = cs->iif;
 986	capi_ctr_down(&iif->ctr);
 987}
 988
 989/*
 990 * kernel CAPI callback methods
 991 * ============================
 992 */
 993
 994/*
 995 * register CAPI application
 996 */
 997static void gigaset_register_appl(struct capi_ctr *ctr, u16 appl,
 998				  capi_register_params *rp)
 999{
1000	struct gigaset_capi_ctr *iif
1001		= container_of(ctr, struct gigaset_capi_ctr, ctr);
1002	struct cardstate *cs = ctr->driverdata;
1003	struct gigaset_capi_appl *ap;
1004
1005	gig_dbg(DEBUG_CMD, "%s [%u] l3cnt=%u blkcnt=%u blklen=%u",
1006		__func__, appl, rp->level3cnt, rp->datablkcnt, rp->datablklen);
1007
1008	list_for_each_entry(ap, &iif->appls, ctrlist)
1009		if (ap->id == appl) {
1010			dev_notice(cs->dev,
1011				   "application %u already registered\n", appl);
1012			return;
1013		}
1014
1015	ap = kzalloc(sizeof(*ap), GFP_KERNEL);
1016	if (!ap) {
1017		dev_err(cs->dev, "%s: out of memory\n", __func__);
1018		return;
1019	}
1020	ap->id = appl;
1021	ap->rp = *rp;
1022
1023	list_add(&ap->ctrlist, &iif->appls);
1024	dev_info(cs->dev, "application %u registered\n", ap->id);
1025}
1026
1027/*
1028 * remove CAPI application from channel
1029 * helper function to keep indentation levels down and stay in 80 columns
1030 */
1031
1032static inline void remove_appl_from_channel(struct bc_state *bcs,
1033					    struct gigaset_capi_appl *ap)
1034{
1035	struct cardstate *cs = bcs->cs;
1036	struct gigaset_capi_appl *bcap;
1037	unsigned long flags;
1038	int prevconnstate;
1039
1040	spin_lock_irqsave(&bcs->aplock, flags);
1041	bcap = bcs->ap;
1042	if (bcap == NULL) {
1043		spin_unlock_irqrestore(&bcs->aplock, flags);
1044		return;
1045	}
1046
1047	/* check first application on channel */
1048	if (bcap == ap) {
1049		bcs->ap = ap->bcnext;
1050		if (bcs->ap != NULL) {
1051			spin_unlock_irqrestore(&bcs->aplock, flags);
1052			return;
1053		}
1054
1055		/* none left, clear channel state */
1056		prevconnstate = bcs->apconnstate;
1057		bcs->apconnstate = APCONN_NONE;
1058		spin_unlock_irqrestore(&bcs->aplock, flags);
1059
1060		if (prevconnstate == APCONN_ACTIVE) {
1061			dev_notice(cs->dev, "%s: hanging up channel %u\n",
1062				   __func__, bcs->channel);
1063			gigaset_add_event(cs, &bcs->at_state,
1064					  EV_HUP, NULL, 0, NULL);
1065			gigaset_schedule_event(cs);
1066		}
1067		return;
1068	}
1069
1070	/* check remaining list */
1071	do {
1072		if (bcap->bcnext == ap) {
1073			bcap->bcnext = bcap->bcnext->bcnext;
1074			spin_unlock_irqrestore(&bcs->aplock, flags);
1075			return;
1076		}
1077		bcap = bcap->bcnext;
1078	} while (bcap != NULL);
1079	spin_unlock_irqrestore(&bcs->aplock, flags);
1080}
1081
1082/*
1083 * release CAPI application
1084 */
1085static void gigaset_release_appl(struct capi_ctr *ctr, u16 appl)
1086{
1087	struct gigaset_capi_ctr *iif
1088		= container_of(ctr, struct gigaset_capi_ctr, ctr);
1089	struct cardstate *cs = iif->ctr.driverdata;
1090	struct gigaset_capi_appl *ap, *tmp;
1091	unsigned ch;
1092
1093	gig_dbg(DEBUG_CMD, "%s [%u]", __func__, appl);
1094
1095	list_for_each_entry_safe(ap, tmp, &iif->appls, ctrlist)
1096		if (ap->id == appl) {
1097			/* remove from any channels */
1098			for (ch = 0; ch < cs->channels; ch++)
1099				remove_appl_from_channel(&cs->bcs[ch], ap);
1100
1101			/* remove from registration list */
1102			list_del(&ap->ctrlist);
1103			kfree(ap);
1104			dev_info(cs->dev, "application %u released\n", appl);
1105		}
1106}
1107
1108/*
1109 * =====================================================================
1110 * outgoing CAPI message handler
1111 * =====================================================================
1112 */
1113
1114/*
1115 * helper function: emit reply message with given Info value
1116 */
1117static void send_conf(struct gigaset_capi_ctr *iif,
1118		      struct gigaset_capi_appl *ap,
1119		      struct sk_buff *skb,
1120		      u16 info)
1121{
1122	struct cardstate *cs = iif->ctr.driverdata;
1123
1124	/*
1125	 * _CONF replies always only have NCCI and Info parameters
1126	 * so they'll fit into the _REQ message skb
1127	 */
1128	capi_cmsg_answer(&iif->acmsg);
1129	iif->acmsg.Info = info;
1130	if (capi_cmsg2message(&iif->acmsg, skb->data)) {
1131		dev_err(cs->dev, "%s: message parser failure\n", __func__);
1132		dev_kfree_skb_any(skb);
1133		return;
1134	}
1135	__skb_trim(skb, CAPI_STDCONF_LEN);
1136	dump_cmsg(DEBUG_CMD, __func__, &iif->acmsg);
1137	capi_ctr_handle_message(&iif->ctr, ap->id, skb);
1138}
1139
1140/*
1141 * process FACILITY_REQ message
1142 */
1143static void do_facility_req(struct gigaset_capi_ctr *iif,
1144			    struct gigaset_capi_appl *ap,
1145			    struct sk_buff *skb)
1146{
1147	struct cardstate *cs = iif->ctr.driverdata;
1148	_cmsg *cmsg = &iif->acmsg;
1149	struct sk_buff *cskb;
1150	u8 *pparam;
1151	unsigned int msgsize = CAPI_FACILITY_CONF_BASELEN;
1152	u16 function, info;
1153	static u8 confparam[10];	/* max. 9 octets + length byte */
1154
1155	/* decode message */
1156	if (capi_message2cmsg(cmsg, skb->data)) {
1157		dev_err(cs->dev, "%s: message parser failure\n", __func__);
1158		dev_kfree_skb_any(skb);
1159		return;
1160	}
1161	dump_cmsg(DEBUG_CMD, __func__, cmsg);
1162
1163	/*
1164	 * Facility Request Parameter is not decoded by capi_message2cmsg()
1165	 * encoding depends on Facility Selector
1166	 */
1167	switch (cmsg->FacilitySelector) {
1168	case CAPI_FACILITY_DTMF:	/* ToDo */
1169		info = CapiFacilityNotSupported;
1170		confparam[0] = 2;	/* length */
1171		/* DTMF information: Unknown DTMF request */
1172		capimsg_setu16(confparam, 1, 2);
1173		break;
1174
1175	case CAPI_FACILITY_V42BIS:	/* not supported */
1176		info = CapiFacilityNotSupported;
1177		confparam[0] = 2;	/* length */
1178		/* V.42 bis information: not available */
1179		capimsg_setu16(confparam, 1, 1);
1180		break;
1181
1182	case CAPI_FACILITY_SUPPSVC:
1183		/* decode Function parameter */
1184		pparam = cmsg->FacilityRequestParameter;
1185		if (pparam == NULL || pparam[0] < 2) {
1186			dev_notice(cs->dev, "%s: %s missing\n", "FACILITY_REQ",
1187				   "Facility Request Parameter");
1188			send_conf(iif, ap, skb, CapiIllMessageParmCoding);
1189			return;
1190		}
1191		function = CAPIMSG_U16(pparam, 1);
1192		switch (function) {
1193		case CAPI_SUPPSVC_GETSUPPORTED:
1194			info = CapiSuccess;
1195			/* Supplementary Service specific parameter */
1196			confparam[3] = 6;	/* length */
1197			/* Supplementary services info: Success */
1198			capimsg_setu16(confparam, 4, CapiSuccess);
1199			/* Supported Services: none */
1200			capimsg_setu32(confparam, 6, 0);
1201			break;
1202		case CAPI_SUPPSVC_LISTEN:
1203			if (pparam[0] < 7 || pparam[3] < 4) {
1204				dev_notice(cs->dev, "%s: %s missing\n",
1205					   "FACILITY_REQ", "Notification Mask");
1206				send_conf(iif, ap, skb,
1207					  CapiIllMessageParmCoding);
1208				return;
1209			}
1210			if (CAPIMSG_U32(pparam, 4) != 0) {
1211				dev_notice(cs->dev,
1212					   "%s: unsupported supplementary service notification mask 0x%x\n",
1213					   "FACILITY_REQ", CAPIMSG_U32(pparam, 4));
1214				info = CapiFacilitySpecificFunctionNotSupported;
1215				confparam[3] = 2;	/* length */
1216				capimsg_setu16(confparam, 4,
1217					       CapiSupplementaryServiceNotSupported);
1218				break;
1219			}
1220			info = CapiSuccess;
1221			confparam[3] = 2;	/* length */
1222			capimsg_setu16(confparam, 4, CapiSuccess);
1223			break;
1224
1225		/* ToDo: add supported services */
1226
1227		default:
1228			dev_notice(cs->dev,
1229				   "%s: unsupported supplementary service function 0x%04x\n",
1230				   "FACILITY_REQ", function);
1231			info = CapiFacilitySpecificFunctionNotSupported;
1232			/* Supplementary Service specific parameter */
1233			confparam[3] = 2;	/* length */
1234			/* Supplementary services info: not supported */
1235			capimsg_setu16(confparam, 4,
1236				       CapiSupplementaryServiceNotSupported);
1237		}
1238
1239		/* Facility confirmation parameter */
1240		confparam[0] = confparam[3] + 3;	/* total length */
1241		/* Function: copy from _REQ message */
1242		capimsg_setu16(confparam, 1, function);
1243		/* Supplementary Service specific parameter already set above */
1244		break;
1245
1246	case CAPI_FACILITY_WAKEUP:	/* ToDo */
1247		info = CapiFacilityNotSupported;
1248		confparam[0] = 2;	/* length */
1249		/* Number of accepted awake request parameters: 0 */
1250		capimsg_setu16(confparam, 1, 0);
1251		break;
1252
1253	default:
1254		info = CapiFacilityNotSupported;
1255		confparam[0] = 0;	/* empty struct */
1256	}
1257
1258	/* send FACILITY_CONF with given Info and confirmation parameter */
1259	dev_kfree_skb_any(skb);
1260	capi_cmsg_answer(cmsg);
1261	cmsg->Info = info;
1262	cmsg->FacilityConfirmationParameter = confparam;
1263	msgsize += confparam[0];	/* length */
1264	cskb = alloc_skb(msgsize, GFP_ATOMIC);
1265	if (!cskb) {
1266		dev_err(cs->dev, "%s: out of memory\n", __func__);
1267		return;
1268	}
1269	if (capi_cmsg2message(cmsg, __skb_put(cskb, msgsize))) {
1270		dev_err(cs->dev, "%s: message parser failure\n", __func__);
1271		dev_kfree_skb_any(cskb);
1272		return;
1273	}
1274	dump_cmsg(DEBUG_CMD, __func__, cmsg);
1275	capi_ctr_handle_message(&iif->ctr, ap->id, cskb);
1276}
1277
1278
1279/*
1280 * process LISTEN_REQ message
1281 * just store the masks in the application data structure
1282 */
1283static void do_listen_req(struct gigaset_capi_ctr *iif,
1284			  struct gigaset_capi_appl *ap,
1285			  struct sk_buff *skb)
1286{
1287	struct cardstate *cs = iif->ctr.driverdata;
1288
1289	/* decode message */
1290	if (capi_message2cmsg(&iif->acmsg, skb->data)) {
1291		dev_err(cs->dev, "%s: message parser failure\n", __func__);
1292		dev_kfree_skb_any(skb);
1293		return;
1294	}
1295	dump_cmsg(DEBUG_CMD, __func__, &iif->acmsg);
1296
1297	/* store listening parameters */
1298	ap->listenInfoMask = iif->acmsg.InfoMask;
1299	ap->listenCIPmask = iif->acmsg.CIPmask;
1300	send_conf(iif, ap, skb, CapiSuccess);
1301}
1302
1303/*
1304 * process ALERT_REQ message
1305 * nothing to do, Gigaset always alerts anyway
1306 */
1307static void do_alert_req(struct gigaset_capi_ctr *iif,
1308			 struct gigaset_capi_appl *ap,
1309			 struct sk_buff *skb)
1310{
1311	struct cardstate *cs = iif->ctr.driverdata;
1312
1313	/* decode message */
1314	if (capi_message2cmsg(&iif->acmsg, skb->data)) {
1315		dev_err(cs->dev, "%s: message parser failure\n", __func__);
1316		dev_kfree_skb_any(skb);
1317		return;
1318	}
1319	dump_cmsg(DEBUG_CMD, __func__, &iif->acmsg);
1320	send_conf(iif, ap, skb, CapiAlertAlreadySent);
1321}
1322
1323/*
1324 * process CONNECT_REQ message
1325 * allocate a B channel, prepare dial commands, queue a DIAL event,
1326 * emit CONNECT_CONF reply
1327 */
1328static void do_connect_req(struct gigaset_capi_ctr *iif,
1329			   struct gigaset_capi_appl *ap,
1330			   struct sk_buff *skb)
1331{
1332	struct cardstate *cs = iif->ctr.driverdata;
1333	_cmsg *cmsg = &iif->acmsg;
1334	struct bc_state *bcs;
1335	char **commands;
1336	char *s;
1337	u8 *pp;
1338	unsigned long flags;
1339	int i, l, lbc, lhlc;
1340	u16 info;
1341
1342	/* decode message */
1343	if (capi_message2cmsg(cmsg, skb->data)) {
1344		dev_err(cs->dev, "%s: message parser failure\n", __func__);
1345		dev_kfree_skb_any(skb);
1346		return;
1347	}
1348	dump_cmsg(DEBUG_CMD, __func__, cmsg);
1349
1350	/* get free B channel & construct PLCI */
1351	bcs = gigaset_get_free_channel(cs);
1352	if (!bcs) {
1353		dev_notice(cs->dev, "%s: no B channel available\n",
1354			   "CONNECT_REQ");
1355		send_conf(iif, ap, skb, CapiNoPlciAvailable);
1356		return;
1357	}
1358	spin_lock_irqsave(&bcs->aplock, flags);
1359	if (bcs->ap != NULL || bcs->apconnstate != APCONN_NONE)
1360		dev_warn(cs->dev, "%s: channel not properly cleared (%p/%d)\n",
1361			 __func__, bcs->ap, bcs->apconnstate);
1362	ap->bcnext = NULL;
1363	bcs->ap = ap;
1364	bcs->apconnstate = APCONN_SETUP;
1365	spin_unlock_irqrestore(&bcs->aplock, flags);
1366
1367	bcs->rx_bufsize = ap->rp.datablklen;
1368	dev_kfree_skb(bcs->rx_skb);
1369	gigaset_new_rx_skb(bcs);
1370	cmsg->adr.adrPLCI |= (bcs->channel + 1) << 8;
1371
1372	/* build command table */
1373	commands = kzalloc(AT_NUM * (sizeof *commands), GFP_KERNEL);
1374	if (!commands)
1375		goto oom;
1376
1377	/* encode parameter: Called party number */
1378	pp = cmsg->CalledPartyNumber;
1379	if (pp == NULL || *pp == 0) {
1380		dev_notice(cs->dev, "%s: %s missing\n",
1381			   "CONNECT_REQ", "Called party number");
1382		info = CapiIllMessageParmCoding;
1383		goto error;
1384	}
1385	l = *pp++;
1386	/* check type of number/numbering plan byte */
1387	switch (*pp) {
1388	case 0x80:	/* unknown type / unknown numbering plan */
1389	case 0x81:	/* unknown type / ISDN/Telephony numbering plan */
1390		break;
1391	default:	/* others: warn about potential misinterpretation */
1392		dev_notice(cs->dev, "%s: %s type/plan 0x%02x unsupported\n",
1393			   "CONNECT_REQ", "Called party number", *pp);
1394	}
1395	pp++;
1396	l--;
1397	/* translate "**" internal call prefix to CTP value */
1398	if (l >= 2 && pp[0] == '*' && pp[1] == '*') {
1399		s = "^SCTP=0\r";
1400		pp += 2;
1401		l -= 2;
1402	} else {
1403		s = "^SCTP=1\r";
1404	}
1405	commands[AT_TYPE] = kstrdup(s, GFP_KERNEL);
1406	if (!commands[AT_TYPE])
1407		goto oom;
1408	commands[AT_DIAL] = kmalloc(l + 3, GFP_KERNEL);
1409	if (!commands[AT_DIAL])
1410		goto oom;
1411	snprintf(commands[AT_DIAL], l + 3, "D%.*s\r", l, pp);
1412
1413	/* encode parameter: Calling party number */
1414	pp = cmsg->CallingPartyNumber;
1415	if (pp != NULL && *pp > 0) {
1416		l = *pp++;
1417
1418		/* check type of number/numbering plan byte */
1419		/* ToDo: allow for/handle Ext=1? */
1420		switch (*pp) {
1421		case 0x00:	/* unknown type / unknown numbering plan */
1422		case 0x01:	/* unknown type / ISDN/Telephony num. plan */
1423			break;
1424		default:
1425			dev_notice(cs->dev,
1426				   "%s: %s type/plan 0x%02x unsupported\n",
1427				   "CONNECT_REQ", "Calling party number", *pp);
1428		}
1429		pp++;
1430		l--;
1431
1432		/* check presentation indicator */
1433		if (!l) {
1434			dev_notice(cs->dev, "%s: %s IE truncated\n",
1435				   "CONNECT_REQ", "Calling party number");
1436			info = CapiIllMessageParmCoding;
1437			goto error;
1438		}
1439		switch (*pp & 0xfc) { /* ignore Screening indicator */
1440		case 0x80:	/* Presentation allowed */
1441			s = "^SCLIP=1\r";
1442			break;
1443		case 0xa0:	/* Presentation restricted */
1444			s = "^SCLIP=0\r";
1445			break;
1446		default:
1447			dev_notice(cs->dev, "%s: invalid %s 0x%02x\n",
1448				   "CONNECT_REQ",
1449				   "Presentation/Screening indicator",
1450				   *pp);
1451			s = "^SCLIP=1\r";
1452		}
1453		commands[AT_CLIP] = kstrdup(s, GFP_KERNEL);
1454		if (!commands[AT_CLIP])
1455			goto oom;
1456		pp++;
1457		l--;
1458
1459		if (l) {
1460			/* number */
1461			commands[AT_MSN] = kmalloc(l + 8, GFP_KERNEL);
1462			if (!commands[AT_MSN])
1463				goto oom;
1464			snprintf(commands[AT_MSN], l + 8, "^SMSN=%*s\r", l, pp);
1465		}
1466	}
1467
1468	/* check parameter: CIP Value */
1469	if (cmsg->CIPValue >= ARRAY_SIZE(cip2bchlc) ||
1470	    (cmsg->CIPValue > 0 && cip2bchlc[cmsg->CIPValue].bc == NULL)) {
1471		dev_notice(cs->dev, "%s: unknown CIP value %d\n",
1472			   "CONNECT_REQ", cmsg->CIPValue);
1473		info = CapiCipValueUnknown;
1474		goto error;
1475	}
1476
1477	/*
1478	 * check/encode parameters: BC & HLC
1479	 * must be encoded together as device doesn't accept HLC separately
1480	 * explicit parameters override values derived from CIP
1481	 */
1482
1483	/* determine lengths */
1484	if (cmsg->BC && cmsg->BC[0])		/* BC specified explicitly */
1485		lbc = 2 * cmsg->BC[0];
1486	else if (cip2bchlc[cmsg->CIPValue].bc)	/* BC derived from CIP */
1487		lbc = strlen(cip2bchlc[cmsg->CIPValue].bc);
1488	else					/* no BC */
1489		lbc = 0;
1490	if (cmsg->HLC && cmsg->HLC[0])		/* HLC specified explicitly */
1491		lhlc = 2 * cmsg->HLC[0];
1492	else if (cip2bchlc[cmsg->CIPValue].hlc)	/* HLC derived from CIP */
1493		lhlc = strlen(cip2bchlc[cmsg->CIPValue].hlc);
1494	else					/* no HLC */
1495		lhlc = 0;
1496
1497	if (lbc) {
1498		/* have BC: allocate and assemble command string */
1499		l = lbc + 7;		/* "^SBC=" + value + "\r" + null byte */
1500		if (lhlc)
1501			l += lhlc + 7;	/* ";^SHLC=" + value */
1502		commands[AT_BC] = kmalloc(l, GFP_KERNEL);
1503		if (!commands[AT_BC])
1504			goto oom;
1505		strcpy(commands[AT_BC], "^SBC=");
1506		if (cmsg->BC && cmsg->BC[0])	/* BC specified explicitly */
1507			decode_ie(cmsg->BC, commands[AT_BC] + 5);
1508		else				/* BC derived from CIP */
1509			strcpy(commands[AT_BC] + 5,
1510			       cip2bchlc[cmsg->CIPValue].bc);
1511		if (lhlc) {
1512			strcpy(commands[AT_BC] + lbc + 5, ";^SHLC=");
1513			if (cmsg->HLC && cmsg->HLC[0])
1514				/* HLC specified explicitly */
1515				decode_ie(cmsg->HLC,
1516					  commands[AT_BC] + lbc + 12);
1517			else	/* HLC derived from CIP */
1518				strcpy(commands[AT_BC] + lbc + 12,
1519				       cip2bchlc[cmsg->CIPValue].hlc);
1520		}
1521		strcpy(commands[AT_BC] + l - 2, "\r");
1522	} else {
1523		/* no BC */
1524		if (lhlc) {
1525			dev_notice(cs->dev, "%s: cannot set HLC without BC\n",
1526				   "CONNECT_REQ");
1527			info = CapiIllMessageParmCoding; /* ? */
1528			goto error;
1529		}
1530	}
1531
1532	/* check/encode parameter: B Protocol */
1533	if (cmsg->BProtocol == CAPI_DEFAULT) {
1534		bcs->proto2 = L2_HDLC;
1535		dev_warn(cs->dev,
1536			 "B2 Protocol X.75 SLP unsupported, using Transparent\n");
1537	} else {
1538		switch (cmsg->B1protocol) {
1539		case 0:
1540			bcs->proto2 = L2_HDLC;
1541			break;
1542		case 1:
1543			bcs->proto2 = L2_VOICE;
1544			break;
1545		default:
1546			dev_warn(cs->dev,
1547				 "B1 Protocol %u unsupported, using Transparent\n",
1548				 cmsg->B1protocol);
1549			bcs->proto2 = L2_VOICE;
1550		}
1551		if (cmsg->B2protocol != 1)
1552			dev_warn(cs->dev,
1553				 "B2 Protocol %u unsupported, using Transparent\n",
1554				 cmsg->B2protocol);
1555		if (cmsg->B3protocol != 0)
1556			dev_warn(cs->dev,
1557				 "B3 Protocol %u unsupported, using Transparent\n",
1558				 cmsg->B3protocol);
1559		ignore_cstruct_param(cs, cmsg->B1configuration,
1560				     "CONNECT_REQ", "B1 Configuration");
1561		ignore_cstruct_param(cs, cmsg->B2configuration,
1562				     "CONNECT_REQ", "B2 Configuration");
1563		ignore_cstruct_param(cs, cmsg->B3configuration,
1564				     "CONNECT_REQ", "B3 Configuration");
1565	}
1566	commands[AT_PROTO] = kmalloc(9, GFP_KERNEL);
1567	if (!commands[AT_PROTO])
1568		goto oom;
1569	snprintf(commands[AT_PROTO], 9, "^SBPR=%u\r", bcs->proto2);
1570
1571	/* ToDo: check/encode remaining parameters */
1572	ignore_cstruct_param(cs, cmsg->CalledPartySubaddress,
1573			     "CONNECT_REQ", "Called pty subaddr");
1574	ignore_cstruct_param(cs, cmsg->CallingPartySubaddress,
1575			     "CONNECT_REQ", "Calling pty subaddr");
1576	ignore_cstruct_param(cs, cmsg->LLC,
1577			     "CONNECT_REQ", "LLC");
1578	if (cmsg->AdditionalInfo != CAPI_DEFAULT) {
1579		ignore_cstruct_param(cs, cmsg->BChannelinformation,
1580				     "CONNECT_REQ", "B Channel Information");
1581		ignore_cstruct_param(cs, cmsg->Keypadfacility,
1582				     "CONNECT_REQ", "Keypad Facility");
1583		ignore_cstruct_param(cs, cmsg->Useruserdata,
1584				     "CONNECT_REQ", "User-User Data");
1585		ignore_cstruct_param(cs, cmsg->Facilitydataarray,
1586				     "CONNECT_REQ", "Facility Data Array");
1587	}
1588
1589	/* encode parameter: B channel to use */
1590	commands[AT_ISO] = kmalloc(9, GFP_KERNEL);
1591	if (!commands[AT_ISO])
1592		goto oom;
1593	snprintf(commands[AT_ISO], 9, "^SISO=%u\r",
1594		 (unsigned) bcs->channel + 1);
1595
1596	/* queue & schedule EV_DIAL event */
1597	if (!gigaset_add_event(cs, &bcs->at_state, EV_DIAL, commands,
1598			       bcs->at_state.seq_index, NULL)) {
1599		info = CAPI_MSGOSRESOURCEERR;
1600		goto error;
1601	}
1602	gigaset_schedule_event(cs);
1603	send_conf(iif, ap, skb, CapiSuccess);
1604	return;
1605
1606oom:
1607	dev_err(cs->dev, "%s: out of memory\n", __func__);
1608	info = CAPI_MSGOSRESOURCEERR;
1609error:
1610	if (commands)
1611		for (i = 0; i < AT_NUM; i++)
1612			kfree(commands[i]);
1613	kfree(commands);
1614	gigaset_free_channel(bcs);
1615	send_conf(iif, ap, skb, info);
1616}
1617
1618/*
1619 * process CONNECT_RESP message
1620 * checks protocol parameters and queues an ACCEPT or HUP event
1621 */
1622static void do_connect_resp(struct gigaset_capi_ctr *iif,
1623			    struct gigaset_capi_appl *ap,
1624			    struct sk_buff *skb)
1625{
1626	struct cardstate *cs = iif->ctr.driverdata;
1627	_cmsg *cmsg = &iif->acmsg;
1628	struct bc_state *bcs;
1629	struct gigaset_capi_appl *oap;
1630	unsigned long flags;
1631	int channel;
1632
1633	/* decode message */
1634	if (capi_message2cmsg(cmsg, skb->data)) {
1635		dev_err(cs->dev, "%s: message parser failure\n", __func__);
1636		dev_kfree_skb_any(skb);
1637		return;
1638	}
1639	dump_cmsg(DEBUG_CMD, __func__, cmsg);
1640	dev_kfree_skb_any(skb);
1641
1642	/* extract and check channel number from PLCI */
1643	channel = (cmsg->adr.adrPLCI >> 8) & 0xff;
1644	if (!channel || channel > cs->channels) {
1645		dev_notice(cs->dev, "%s: invalid %s 0x%02x\n",
1646			   "CONNECT_RESP", "PLCI", cmsg->adr.adrPLCI);
1647		return;
1648	}
1649	bcs = cs->bcs + channel - 1;
1650
1651	switch (cmsg->Reject) {
1652	case 0:		/* Accept */
1653		/* drop all competing applications, keep only this one */
1654		spin_lock_irqsave(&bcs->aplock, flags);
1655		while (bcs->ap != NULL) {
1656			oap = bcs->ap;
1657			bcs->ap = oap->bcnext;
1658			if (oap != ap) {
1659				spin_unlock_irqrestore(&bcs->aplock, flags);
1660				send_disconnect_ind(bcs, oap,
1661						    CapiCallGivenToOtherApplication);
1662				spin_lock_irqsave(&bcs->aplock, flags);
1663			}
1664		}
1665		ap->bcnext = NULL;
1666		bcs->ap = ap;
1667		spin_unlock_irqrestore(&bcs->aplock, flags);
1668
1669		bcs->rx_bufsize = ap->rp.datablklen;
1670		dev_kfree_skb(bcs->rx_skb);
1671		gigaset_new_rx_skb(bcs);
1672		bcs->chstate |= CHS_NOTIFY_LL;
1673
1674		/* check/encode B channel protocol */
1675		if (cmsg->BProtocol == CAPI_DEFAULT) {
1676			bcs->proto2 = L2_HDLC;
1677			dev_warn(cs->dev,
1678				 "B2 Protocol X.75 SLP unsupported, using Transparent\n");
1679		} else {
1680			switch (cmsg->B1protocol) {
1681			case 0:
1682				bcs->proto2 = L2_HDLC;
1683				break;
1684			case 1:
1685				bcs->proto2 = L2_VOICE;
1686				break;
1687			default:
1688				dev_warn(cs->dev,
1689					 "B1 Protocol %u unsupported, using Transparent\n",
1690					 cmsg->B1protocol);
1691				bcs->proto2 = L2_VOICE;
1692			}
1693			if (cmsg->B2protocol != 1)
1694				dev_warn(cs->dev,
1695					 "B2 Protocol %u unsupported, using Transparent\n",
1696					 cmsg->B2protocol);
1697			if (cmsg->B3protocol != 0)
1698				dev_warn(cs->dev,
1699					 "B3 Protocol %u unsupported, using Transparent\n",
1700					 cmsg->B3protocol);
1701			ignore_cstruct_param(cs, cmsg->B1configuration,
1702					     "CONNECT_RESP", "B1 Configuration");
1703			ignore_cstruct_param(cs, cmsg->B2configuration,
1704					     "CONNECT_RESP", "B2 Configuration");
1705			ignore_cstruct_param(cs, cmsg->B3configuration,
1706					     "CONNECT_RESP", "B3 Configuration");
1707		}
1708
1709		/* ToDo: check/encode remaining parameters */
1710		ignore_cstruct_param(cs, cmsg->ConnectedNumber,
1711				     "CONNECT_RESP", "Connected Number");
1712		ignore_cstruct_param(cs, cmsg->ConnectedSubaddress,
1713				     "CONNECT_RESP", "Connected Subaddress");
1714		ignore_cstruct_param(cs, cmsg->LLC,
1715				     "CONNECT_RESP", "LLC");
1716		if (cmsg->AdditionalInfo != CAPI_DEFAULT) {
1717			ignore_cstruct_param(cs, cmsg->BChannelinformation,
1718					     "CONNECT_RESP", "BChannel Information");
1719			ignore_cstruct_param(cs, cmsg->Keypadfacility,
1720					     "CONNECT_RESP", "Keypad Facility");
1721			ignore_cstruct_param(cs, cmsg->Useruserdata,
1722					     "CONNECT_RESP", "User-User Data");
1723			ignore_cstruct_param(cs, cmsg->Facilitydataarray,
1724					     "CONNECT_RESP", "Facility Data Array");
1725		}
1726
1727		/* Accept call */
1728		if (!gigaset_add_event(cs, &cs->bcs[channel - 1].at_state,
1729				       EV_ACCEPT, NULL, 0, NULL))
1730			return

Large files files are truncated, but you can click here to view the full file