Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
awilliam
GitHub Repository: awilliam/linux-vfio
Path: blob/master/drivers/isdn/capi/kcapi.c
17537 views
1
/* $Id: kcapi.c,v 1.1.2.8 2004/03/26 19:57:20 armin Exp $
2
*
3
* Kernel CAPI 2.0 Module
4
*
5
* Copyright 1999 by Carsten Paeth <[email protected]>
6
* Copyright 2002 by Kai Germaschewski <[email protected]>
7
*
8
* This software may be used and distributed according to the terms
9
* of the GNU General Public License, incorporated herein by reference.
10
*
11
*/
12
13
#define AVMB1_COMPAT
14
15
#include "kcapi.h"
16
#include <linux/module.h>
17
#include <linux/mm.h>
18
#include <linux/interrupt.h>
19
#include <linux/ioport.h>
20
#include <linux/proc_fs.h>
21
#include <linux/sched.h>
22
#include <linux/seq_file.h>
23
#include <linux/skbuff.h>
24
#include <linux/workqueue.h>
25
#include <linux/capi.h>
26
#include <linux/kernelcapi.h>
27
#include <linux/init.h>
28
#include <linux/moduleparam.h>
29
#include <linux/delay.h>
30
#include <linux/slab.h>
31
#include <asm/uaccess.h>
32
#include <linux/isdn/capicmd.h>
33
#include <linux/isdn/capiutil.h>
34
#ifdef AVMB1_COMPAT
35
#include <linux/b1lli.h>
36
#endif
37
#include <linux/mutex.h>
38
#include <linux/rcupdate.h>
39
40
static int showcapimsgs = 0;
41
static struct workqueue_struct *kcapi_wq;
42
43
MODULE_DESCRIPTION("CAPI4Linux: kernel CAPI layer");
44
MODULE_AUTHOR("Carsten Paeth");
45
MODULE_LICENSE("GPL");
46
module_param(showcapimsgs, uint, 0);
47
48
/* ------------------------------------------------------------- */
49
50
struct capictr_event {
51
struct work_struct work;
52
unsigned int type;
53
u32 controller;
54
};
55
56
/* ------------------------------------------------------------- */
57
58
static struct capi_version driver_version = {2, 0, 1, 1<<4};
59
static char driver_serial[CAPI_SERIAL_LEN] = "0004711";
60
static char capi_manufakturer[64] = "AVM Berlin";
61
62
#define NCCI2CTRL(ncci) (((ncci) >> 24) & 0x7f)
63
64
LIST_HEAD(capi_drivers);
65
DEFINE_MUTEX(capi_drivers_lock);
66
67
struct capi_ctr *capi_controller[CAPI_MAXCONTR];
68
DEFINE_MUTEX(capi_controller_lock);
69
70
struct capi20_appl *capi_applications[CAPI_MAXAPPL];
71
72
static int ncontrollers;
73
74
static BLOCKING_NOTIFIER_HEAD(ctr_notifier_list);
75
76
/* -------- controller ref counting -------------------------------------- */
77
78
static inline struct capi_ctr *
79
capi_ctr_get(struct capi_ctr *ctr)
80
{
81
if (!try_module_get(ctr->owner))
82
return NULL;
83
return ctr;
84
}
85
86
static inline void
87
capi_ctr_put(struct capi_ctr *ctr)
88
{
89
module_put(ctr->owner);
90
}
91
92
/* ------------------------------------------------------------- */
93
94
static inline struct capi_ctr *get_capi_ctr_by_nr(u16 contr)
95
{
96
if (contr - 1 >= CAPI_MAXCONTR)
97
return NULL;
98
99
return capi_controller[contr - 1];
100
}
101
102
static inline struct capi20_appl *__get_capi_appl_by_nr(u16 applid)
103
{
104
lockdep_assert_held(&capi_controller_lock);
105
106
if (applid - 1 >= CAPI_MAXAPPL)
107
return NULL;
108
109
return capi_applications[applid - 1];
110
}
111
112
static inline struct capi20_appl *get_capi_appl_by_nr(u16 applid)
113
{
114
if (applid - 1 >= CAPI_MAXAPPL)
115
return NULL;
116
117
return rcu_dereference(capi_applications[applid - 1]);
118
}
119
120
/* -------- util functions ------------------------------------ */
121
122
static inline int capi_cmd_valid(u8 cmd)
123
{
124
switch (cmd) {
125
case CAPI_ALERT:
126
case CAPI_CONNECT:
127
case CAPI_CONNECT_ACTIVE:
128
case CAPI_CONNECT_B3_ACTIVE:
129
case CAPI_CONNECT_B3:
130
case CAPI_CONNECT_B3_T90_ACTIVE:
131
case CAPI_DATA_B3:
132
case CAPI_DISCONNECT_B3:
133
case CAPI_DISCONNECT:
134
case CAPI_FACILITY:
135
case CAPI_INFO:
136
case CAPI_LISTEN:
137
case CAPI_MANUFACTURER:
138
case CAPI_RESET_B3:
139
case CAPI_SELECT_B_PROTOCOL:
140
return 1;
141
}
142
return 0;
143
}
144
145
static inline int capi_subcmd_valid(u8 subcmd)
146
{
147
switch (subcmd) {
148
case CAPI_REQ:
149
case CAPI_CONF:
150
case CAPI_IND:
151
case CAPI_RESP:
152
return 1;
153
}
154
return 0;
155
}
156
157
/* ------------------------------------------------------------ */
158
159
static void
160
register_appl(struct capi_ctr *ctr, u16 applid, capi_register_params *rparam)
161
{
162
ctr = capi_ctr_get(ctr);
163
164
if (ctr)
165
ctr->register_appl(ctr, applid, rparam);
166
else
167
printk(KERN_WARNING "%s: cannot get controller resources\n",
168
__func__);
169
}
170
171
172
static void release_appl(struct capi_ctr *ctr, u16 applid)
173
{
174
DBG("applid %#x", applid);
175
176
ctr->release_appl(ctr, applid);
177
capi_ctr_put(ctr);
178
}
179
180
static void notify_up(u32 contr)
181
{
182
struct capi20_appl *ap;
183
struct capi_ctr *ctr;
184
u16 applid;
185
186
mutex_lock(&capi_controller_lock);
187
188
if (showcapimsgs & 1)
189
printk(KERN_DEBUG "kcapi: notify up contr %d\n", contr);
190
191
ctr = get_capi_ctr_by_nr(contr);
192
if (ctr) {
193
if (ctr->state == CAPI_CTR_RUNNING)
194
goto unlock_out;
195
196
ctr->state = CAPI_CTR_RUNNING;
197
198
for (applid = 1; applid <= CAPI_MAXAPPL; applid++) {
199
ap = __get_capi_appl_by_nr(applid);
200
if (ap)
201
register_appl(ctr, applid, &ap->rparam);
202
}
203
204
wake_up_interruptible_all(&ctr->state_wait_queue);
205
} else
206
printk(KERN_WARNING "%s: invalid contr %d\n", __func__, contr);
207
208
unlock_out:
209
mutex_unlock(&capi_controller_lock);
210
}
211
212
static void ctr_down(struct capi_ctr *ctr, int new_state)
213
{
214
struct capi20_appl *ap;
215
u16 applid;
216
217
if (ctr->state == CAPI_CTR_DETECTED || ctr->state == CAPI_CTR_DETACHED)
218
return;
219
220
ctr->state = new_state;
221
222
memset(ctr->manu, 0, sizeof(ctr->manu));
223
memset(&ctr->version, 0, sizeof(ctr->version));
224
memset(&ctr->profile, 0, sizeof(ctr->profile));
225
memset(ctr->serial, 0, sizeof(ctr->serial));
226
227
for (applid = 1; applid <= CAPI_MAXAPPL; applid++) {
228
ap = __get_capi_appl_by_nr(applid);
229
if (ap)
230
capi_ctr_put(ctr);
231
}
232
233
wake_up_interruptible_all(&ctr->state_wait_queue);
234
}
235
236
static void notify_down(u32 contr)
237
{
238
struct capi_ctr *ctr;
239
240
mutex_lock(&capi_controller_lock);
241
242
if (showcapimsgs & 1)
243
printk(KERN_DEBUG "kcapi: notify down contr %d\n", contr);
244
245
ctr = get_capi_ctr_by_nr(contr);
246
if (ctr)
247
ctr_down(ctr, CAPI_CTR_DETECTED);
248
else
249
printk(KERN_WARNING "%s: invalid contr %d\n", __func__, contr);
250
251
mutex_unlock(&capi_controller_lock);
252
}
253
254
static int
255
notify_handler(struct notifier_block *nb, unsigned long val, void *v)
256
{
257
u32 contr = (long)v;
258
259
switch (val) {
260
case CAPICTR_UP:
261
notify_up(contr);
262
break;
263
case CAPICTR_DOWN:
264
notify_down(contr);
265
break;
266
}
267
return NOTIFY_OK;
268
}
269
270
static void do_notify_work(struct work_struct *work)
271
{
272
struct capictr_event *event =
273
container_of(work, struct capictr_event, work);
274
275
blocking_notifier_call_chain(&ctr_notifier_list, event->type,
276
(void *)(long)event->controller);
277
kfree(event);
278
}
279
280
/*
281
* The notifier will result in adding/deleteing of devices. Devices can
282
* only removed in user process, not in bh.
283
*/
284
static int notify_push(unsigned int event_type, u32 controller)
285
{
286
struct capictr_event *event = kmalloc(sizeof(*event), GFP_ATOMIC);
287
288
if (!event)
289
return -ENOMEM;
290
291
INIT_WORK(&event->work, do_notify_work);
292
event->type = event_type;
293
event->controller = controller;
294
295
queue_work(kcapi_wq, &event->work);
296
return 0;
297
}
298
299
int register_capictr_notifier(struct notifier_block *nb)
300
{
301
return blocking_notifier_chain_register(&ctr_notifier_list, nb);
302
}
303
EXPORT_SYMBOL_GPL(register_capictr_notifier);
304
305
int unregister_capictr_notifier(struct notifier_block *nb)
306
{
307
return blocking_notifier_chain_unregister(&ctr_notifier_list, nb);
308
}
309
EXPORT_SYMBOL_GPL(unregister_capictr_notifier);
310
311
/* -------- Receiver ------------------------------------------ */
312
313
static void recv_handler(struct work_struct *work)
314
{
315
struct sk_buff *skb;
316
struct capi20_appl *ap =
317
container_of(work, struct capi20_appl, recv_work);
318
319
if ((!ap) || (ap->release_in_progress))
320
return;
321
322
mutex_lock(&ap->recv_mtx);
323
while ((skb = skb_dequeue(&ap->recv_queue))) {
324
if (CAPIMSG_CMD(skb->data) == CAPI_DATA_B3_IND)
325
ap->nrecvdatapkt++;
326
else
327
ap->nrecvctlpkt++;
328
329
ap->recv_message(ap, skb);
330
}
331
mutex_unlock(&ap->recv_mtx);
332
}
333
334
/**
335
* capi_ctr_handle_message() - handle incoming CAPI message
336
* @ctr: controller descriptor structure.
337
* @appl: application ID.
338
* @skb: message.
339
*
340
* Called by hardware driver to pass a CAPI message to the application.
341
*/
342
343
void capi_ctr_handle_message(struct capi_ctr *ctr, u16 appl,
344
struct sk_buff *skb)
345
{
346
struct capi20_appl *ap;
347
int showctl = 0;
348
u8 cmd, subcmd;
349
_cdebbuf *cdb;
350
351
if (ctr->state != CAPI_CTR_RUNNING) {
352
cdb = capi_message2str(skb->data);
353
if (cdb) {
354
printk(KERN_INFO "kcapi: controller [%03d] not active, got: %s",
355
ctr->cnr, cdb->buf);
356
cdebbuf_free(cdb);
357
} else
358
printk(KERN_INFO "kcapi: controller [%03d] not active, cannot trace\n",
359
ctr->cnr);
360
goto error;
361
}
362
363
cmd = CAPIMSG_COMMAND(skb->data);
364
subcmd = CAPIMSG_SUBCOMMAND(skb->data);
365
if (cmd == CAPI_DATA_B3 && subcmd == CAPI_IND) {
366
ctr->nrecvdatapkt++;
367
if (ctr->traceflag > 2)
368
showctl |= 2;
369
} else {
370
ctr->nrecvctlpkt++;
371
if (ctr->traceflag)
372
showctl |= 2;
373
}
374
showctl |= (ctr->traceflag & 1);
375
if (showctl & 2) {
376
if (showctl & 1) {
377
printk(KERN_DEBUG "kcapi: got [%03d] id#%d %s len=%u\n",
378
ctr->cnr, CAPIMSG_APPID(skb->data),
379
capi_cmd2str(cmd, subcmd),
380
CAPIMSG_LEN(skb->data));
381
} else {
382
cdb = capi_message2str(skb->data);
383
if (cdb) {
384
printk(KERN_DEBUG "kcapi: got [%03d] %s\n",
385
ctr->cnr, cdb->buf);
386
cdebbuf_free(cdb);
387
} else
388
printk(KERN_DEBUG "kcapi: got [%03d] id#%d %s len=%u, cannot trace\n",
389
ctr->cnr, CAPIMSG_APPID(skb->data),
390
capi_cmd2str(cmd, subcmd),
391
CAPIMSG_LEN(skb->data));
392
}
393
394
}
395
396
rcu_read_lock();
397
ap = get_capi_appl_by_nr(CAPIMSG_APPID(skb->data));
398
if (!ap) {
399
rcu_read_unlock();
400
cdb = capi_message2str(skb->data);
401
if (cdb) {
402
printk(KERN_ERR "kcapi: handle_message: applid %d state released (%s)\n",
403
CAPIMSG_APPID(skb->data), cdb->buf);
404
cdebbuf_free(cdb);
405
} else
406
printk(KERN_ERR "kcapi: handle_message: applid %d state released (%s) cannot trace\n",
407
CAPIMSG_APPID(skb->data),
408
capi_cmd2str(cmd, subcmd));
409
goto error;
410
}
411
skb_queue_tail(&ap->recv_queue, skb);
412
queue_work(kcapi_wq, &ap->recv_work);
413
rcu_read_unlock();
414
415
return;
416
417
error:
418
kfree_skb(skb);
419
}
420
421
EXPORT_SYMBOL(capi_ctr_handle_message);
422
423
/**
424
* capi_ctr_ready() - signal CAPI controller ready
425
* @ctr: controller descriptor structure.
426
*
427
* Called by hardware driver to signal that the controller is up and running.
428
*/
429
430
void capi_ctr_ready(struct capi_ctr *ctr)
431
{
432
printk(KERN_NOTICE "kcapi: controller [%03d] \"%s\" ready.\n",
433
ctr->cnr, ctr->name);
434
435
notify_push(CAPICTR_UP, ctr->cnr);
436
}
437
438
EXPORT_SYMBOL(capi_ctr_ready);
439
440
/**
441
* capi_ctr_down() - signal CAPI controller not ready
442
* @ctr: controller descriptor structure.
443
*
444
* Called by hardware driver to signal that the controller is down and
445
* unavailable for use.
446
*/
447
448
void capi_ctr_down(struct capi_ctr *ctr)
449
{
450
printk(KERN_NOTICE "kcapi: controller [%03d] down.\n", ctr->cnr);
451
452
notify_push(CAPICTR_DOWN, ctr->cnr);
453
}
454
455
EXPORT_SYMBOL(capi_ctr_down);
456
457
/**
458
* capi_ctr_suspend_output() - suspend controller
459
* @ctr: controller descriptor structure.
460
*
461
* Called by hardware driver to stop data flow.
462
*
463
* Note: The caller is responsible for synchronizing concurrent state changes
464
* as well as invocations of capi_ctr_handle_message.
465
*/
466
467
void capi_ctr_suspend_output(struct capi_ctr *ctr)
468
{
469
if (!ctr->blocked) {
470
printk(KERN_DEBUG "kcapi: controller [%03d] suspend\n",
471
ctr->cnr);
472
ctr->blocked = 1;
473
}
474
}
475
476
EXPORT_SYMBOL(capi_ctr_suspend_output);
477
478
/**
479
* capi_ctr_resume_output() - resume controller
480
* @ctr: controller descriptor structure.
481
*
482
* Called by hardware driver to resume data flow.
483
*
484
* Note: The caller is responsible for synchronizing concurrent state changes
485
* as well as invocations of capi_ctr_handle_message.
486
*/
487
488
void capi_ctr_resume_output(struct capi_ctr *ctr)
489
{
490
if (ctr->blocked) {
491
printk(KERN_DEBUG "kcapi: controller [%03d] resumed\n",
492
ctr->cnr);
493
ctr->blocked = 0;
494
}
495
}
496
497
EXPORT_SYMBOL(capi_ctr_resume_output);
498
499
/* ------------------------------------------------------------- */
500
501
/**
502
* attach_capi_ctr() - register CAPI controller
503
* @ctr: controller descriptor structure.
504
*
505
* Called by hardware driver to register a controller with the CAPI subsystem.
506
* Return value: 0 on success, error code < 0 on error
507
*/
508
509
int attach_capi_ctr(struct capi_ctr *ctr)
510
{
511
int i;
512
513
mutex_lock(&capi_controller_lock);
514
515
for (i = 0; i < CAPI_MAXCONTR; i++) {
516
if (!capi_controller[i])
517
break;
518
}
519
if (i == CAPI_MAXCONTR) {
520
mutex_unlock(&capi_controller_lock);
521
printk(KERN_ERR "kcapi: out of controller slots\n");
522
return -EBUSY;
523
}
524
capi_controller[i] = ctr;
525
526
ctr->nrecvctlpkt = 0;
527
ctr->nrecvdatapkt = 0;
528
ctr->nsentctlpkt = 0;
529
ctr->nsentdatapkt = 0;
530
ctr->cnr = i + 1;
531
ctr->state = CAPI_CTR_DETECTED;
532
ctr->blocked = 0;
533
ctr->traceflag = showcapimsgs;
534
init_waitqueue_head(&ctr->state_wait_queue);
535
536
sprintf(ctr->procfn, "capi/controllers/%d", ctr->cnr);
537
ctr->procent = proc_create_data(ctr->procfn, 0, NULL, ctr->proc_fops, ctr);
538
539
ncontrollers++;
540
541
mutex_unlock(&capi_controller_lock);
542
543
printk(KERN_NOTICE "kcapi: controller [%03d]: %s attached\n",
544
ctr->cnr, ctr->name);
545
return 0;
546
}
547
548
EXPORT_SYMBOL(attach_capi_ctr);
549
550
/**
551
* detach_capi_ctr() - unregister CAPI controller
552
* @ctr: controller descriptor structure.
553
*
554
* Called by hardware driver to remove the registration of a controller
555
* with the CAPI subsystem.
556
* Return value: 0 on success, error code < 0 on error
557
*/
558
559
int detach_capi_ctr(struct capi_ctr *ctr)
560
{
561
int err = 0;
562
563
mutex_lock(&capi_controller_lock);
564
565
ctr_down(ctr, CAPI_CTR_DETACHED);
566
567
if (capi_controller[ctr->cnr - 1] != ctr) {
568
err = -EINVAL;
569
goto unlock_out;
570
}
571
capi_controller[ctr->cnr - 1] = NULL;
572
ncontrollers--;
573
574
if (ctr->procent)
575
remove_proc_entry(ctr->procfn, NULL);
576
577
printk(KERN_NOTICE "kcapi: controller [%03d]: %s unregistered\n",
578
ctr->cnr, ctr->name);
579
580
unlock_out:
581
mutex_unlock(&capi_controller_lock);
582
583
return err;
584
}
585
586
EXPORT_SYMBOL(detach_capi_ctr);
587
588
/**
589
* register_capi_driver() - register CAPI driver
590
* @driver: driver descriptor structure.
591
*
592
* Called by hardware driver to register itself with the CAPI subsystem.
593
*/
594
595
void register_capi_driver(struct capi_driver *driver)
596
{
597
mutex_lock(&capi_drivers_lock);
598
list_add_tail(&driver->list, &capi_drivers);
599
mutex_unlock(&capi_drivers_lock);
600
}
601
602
EXPORT_SYMBOL(register_capi_driver);
603
604
/**
605
* unregister_capi_driver() - unregister CAPI driver
606
* @driver: driver descriptor structure.
607
*
608
* Called by hardware driver to unregister itself from the CAPI subsystem.
609
*/
610
611
void unregister_capi_driver(struct capi_driver *driver)
612
{
613
mutex_lock(&capi_drivers_lock);
614
list_del(&driver->list);
615
mutex_unlock(&capi_drivers_lock);
616
}
617
618
EXPORT_SYMBOL(unregister_capi_driver);
619
620
/* ------------------------------------------------------------- */
621
/* -------- CAPI2.0 Interface ---------------------------------- */
622
/* ------------------------------------------------------------- */
623
624
/**
625
* capi20_isinstalled() - CAPI 2.0 operation CAPI_INSTALLED
626
*
627
* Return value: CAPI result code (CAPI_NOERROR if at least one ISDN controller
628
* is ready for use, CAPI_REGNOTINSTALLED otherwise)
629
*/
630
631
u16 capi20_isinstalled(void)
632
{
633
u16 ret = CAPI_REGNOTINSTALLED;
634
int i;
635
636
mutex_lock(&capi_controller_lock);
637
638
for (i = 0; i < CAPI_MAXCONTR; i++)
639
if (capi_controller[i] &&
640
capi_controller[i]->state == CAPI_CTR_RUNNING) {
641
ret = CAPI_NOERROR;
642
break;
643
}
644
645
mutex_unlock(&capi_controller_lock);
646
647
return ret;
648
}
649
650
EXPORT_SYMBOL(capi20_isinstalled);
651
652
/**
653
* capi20_register() - CAPI 2.0 operation CAPI_REGISTER
654
* @ap: CAPI application descriptor structure.
655
*
656
* Register an application's presence with CAPI.
657
* A unique application ID is assigned and stored in @ap->applid.
658
* After this function returns successfully, the message receive
659
* callback function @ap->recv_message() may be called at any time
660
* until capi20_release() has been called for the same @ap.
661
* Return value: CAPI result code
662
*/
663
664
u16 capi20_register(struct capi20_appl *ap)
665
{
666
int i;
667
u16 applid;
668
669
DBG("");
670
671
if (ap->rparam.datablklen < 128)
672
return CAPI_LOGBLKSIZETOSMALL;
673
674
ap->nrecvctlpkt = 0;
675
ap->nrecvdatapkt = 0;
676
ap->nsentctlpkt = 0;
677
ap->nsentdatapkt = 0;
678
mutex_init(&ap->recv_mtx);
679
skb_queue_head_init(&ap->recv_queue);
680
INIT_WORK(&ap->recv_work, recv_handler);
681
ap->release_in_progress = 0;
682
683
mutex_lock(&capi_controller_lock);
684
685
for (applid = 1; applid <= CAPI_MAXAPPL; applid++) {
686
if (capi_applications[applid - 1] == NULL)
687
break;
688
}
689
if (applid > CAPI_MAXAPPL) {
690
mutex_unlock(&capi_controller_lock);
691
return CAPI_TOOMANYAPPLS;
692
}
693
694
ap->applid = applid;
695
capi_applications[applid - 1] = ap;
696
697
for (i = 0; i < CAPI_MAXCONTR; i++) {
698
if (!capi_controller[i] ||
699
capi_controller[i]->state != CAPI_CTR_RUNNING)
700
continue;
701
register_appl(capi_controller[i], applid, &ap->rparam);
702
}
703
704
mutex_unlock(&capi_controller_lock);
705
706
if (showcapimsgs & 1) {
707
printk(KERN_DEBUG "kcapi: appl %d up\n", applid);
708
}
709
710
return CAPI_NOERROR;
711
}
712
713
EXPORT_SYMBOL(capi20_register);
714
715
/**
716
* capi20_release() - CAPI 2.0 operation CAPI_RELEASE
717
* @ap: CAPI application descriptor structure.
718
*
719
* Terminate an application's registration with CAPI.
720
* After this function returns successfully, the message receive
721
* callback function @ap->recv_message() will no longer be called.
722
* Return value: CAPI result code
723
*/
724
725
u16 capi20_release(struct capi20_appl *ap)
726
{
727
int i;
728
729
DBG("applid %#x", ap->applid);
730
731
mutex_lock(&capi_controller_lock);
732
733
ap->release_in_progress = 1;
734
capi_applications[ap->applid - 1] = NULL;
735
736
synchronize_rcu();
737
738
for (i = 0; i < CAPI_MAXCONTR; i++) {
739
if (!capi_controller[i] ||
740
capi_controller[i]->state != CAPI_CTR_RUNNING)
741
continue;
742
release_appl(capi_controller[i], ap->applid);
743
}
744
745
mutex_unlock(&capi_controller_lock);
746
747
flush_workqueue(kcapi_wq);
748
skb_queue_purge(&ap->recv_queue);
749
750
if (showcapimsgs & 1) {
751
printk(KERN_DEBUG "kcapi: appl %d down\n", ap->applid);
752
}
753
754
return CAPI_NOERROR;
755
}
756
757
EXPORT_SYMBOL(capi20_release);
758
759
/**
760
* capi20_put_message() - CAPI 2.0 operation CAPI_PUT_MESSAGE
761
* @ap: CAPI application descriptor structure.
762
* @skb: CAPI message.
763
*
764
* Transfer a single message to CAPI.
765
* Return value: CAPI result code
766
*/
767
768
u16 capi20_put_message(struct capi20_appl *ap, struct sk_buff *skb)
769
{
770
struct capi_ctr *ctr;
771
int showctl = 0;
772
u8 cmd, subcmd;
773
774
DBG("applid %#x", ap->applid);
775
776
if (ncontrollers == 0)
777
return CAPI_REGNOTINSTALLED;
778
if ((ap->applid == 0) || ap->release_in_progress)
779
return CAPI_ILLAPPNR;
780
if (skb->len < 12
781
|| !capi_cmd_valid(CAPIMSG_COMMAND(skb->data))
782
|| !capi_subcmd_valid(CAPIMSG_SUBCOMMAND(skb->data)))
783
return CAPI_ILLCMDORSUBCMDORMSGTOSMALL;
784
785
/*
786
* The controller reference is protected by the existence of the
787
* application passed to us. We assume that the caller properly
788
* synchronizes this service with capi20_release.
789
*/
790
ctr = get_capi_ctr_by_nr(CAPIMSG_CONTROLLER(skb->data));
791
if (!ctr || ctr->state != CAPI_CTR_RUNNING)
792
return CAPI_REGNOTINSTALLED;
793
if (ctr->blocked)
794
return CAPI_SENDQUEUEFULL;
795
796
cmd = CAPIMSG_COMMAND(skb->data);
797
subcmd = CAPIMSG_SUBCOMMAND(skb->data);
798
799
if (cmd == CAPI_DATA_B3 && subcmd== CAPI_REQ) {
800
ctr->nsentdatapkt++;
801
ap->nsentdatapkt++;
802
if (ctr->traceflag > 2)
803
showctl |= 2;
804
} else {
805
ctr->nsentctlpkt++;
806
ap->nsentctlpkt++;
807
if (ctr->traceflag)
808
showctl |= 2;
809
}
810
showctl |= (ctr->traceflag & 1);
811
if (showctl & 2) {
812
if (showctl & 1) {
813
printk(KERN_DEBUG "kcapi: put [%03d] id#%d %s len=%u\n",
814
CAPIMSG_CONTROLLER(skb->data),
815
CAPIMSG_APPID(skb->data),
816
capi_cmd2str(cmd, subcmd),
817
CAPIMSG_LEN(skb->data));
818
} else {
819
_cdebbuf *cdb = capi_message2str(skb->data);
820
if (cdb) {
821
printk(KERN_DEBUG "kcapi: put [%03d] %s\n",
822
CAPIMSG_CONTROLLER(skb->data),
823
cdb->buf);
824
cdebbuf_free(cdb);
825
} else
826
printk(KERN_DEBUG "kcapi: put [%03d] id#%d %s len=%u cannot trace\n",
827
CAPIMSG_CONTROLLER(skb->data),
828
CAPIMSG_APPID(skb->data),
829
capi_cmd2str(cmd, subcmd),
830
CAPIMSG_LEN(skb->data));
831
}
832
}
833
return ctr->send_message(ctr, skb);
834
}
835
836
EXPORT_SYMBOL(capi20_put_message);
837
838
/**
839
* capi20_get_manufacturer() - CAPI 2.0 operation CAPI_GET_MANUFACTURER
840
* @contr: controller number.
841
* @buf: result buffer (64 bytes).
842
*
843
* Retrieve information about the manufacturer of the specified ISDN controller
844
* or (for @contr == 0) the driver itself.
845
* Return value: CAPI result code
846
*/
847
848
u16 capi20_get_manufacturer(u32 contr, u8 *buf)
849
{
850
struct capi_ctr *ctr;
851
u16 ret;
852
853
if (contr == 0) {
854
strlcpy(buf, capi_manufakturer, CAPI_MANUFACTURER_LEN);
855
return CAPI_NOERROR;
856
}
857
858
mutex_lock(&capi_controller_lock);
859
860
ctr = get_capi_ctr_by_nr(contr);
861
if (ctr && ctr->state == CAPI_CTR_RUNNING) {
862
strlcpy(buf, ctr->manu, CAPI_MANUFACTURER_LEN);
863
ret = CAPI_NOERROR;
864
} else
865
ret = CAPI_REGNOTINSTALLED;
866
867
mutex_unlock(&capi_controller_lock);
868
return ret;
869
}
870
871
EXPORT_SYMBOL(capi20_get_manufacturer);
872
873
/**
874
* capi20_get_version() - CAPI 2.0 operation CAPI_GET_VERSION
875
* @contr: controller number.
876
* @verp: result structure.
877
*
878
* Retrieve version information for the specified ISDN controller
879
* or (for @contr == 0) the driver itself.
880
* Return value: CAPI result code
881
*/
882
883
u16 capi20_get_version(u32 contr, struct capi_version *verp)
884
{
885
struct capi_ctr *ctr;
886
u16 ret;
887
888
if (contr == 0) {
889
*verp = driver_version;
890
return CAPI_NOERROR;
891
}
892
893
mutex_lock(&capi_controller_lock);
894
895
ctr = get_capi_ctr_by_nr(contr);
896
if (ctr && ctr->state == CAPI_CTR_RUNNING) {
897
memcpy(verp, &ctr->version, sizeof(capi_version));
898
ret = CAPI_NOERROR;
899
} else
900
ret = CAPI_REGNOTINSTALLED;
901
902
mutex_unlock(&capi_controller_lock);
903
return ret;
904
}
905
906
EXPORT_SYMBOL(capi20_get_version);
907
908
/**
909
* capi20_get_serial() - CAPI 2.0 operation CAPI_GET_SERIAL_NUMBER
910
* @contr: controller number.
911
* @serial: result buffer (8 bytes).
912
*
913
* Retrieve the serial number of the specified ISDN controller
914
* or (for @contr == 0) the driver itself.
915
* Return value: CAPI result code
916
*/
917
918
u16 capi20_get_serial(u32 contr, u8 *serial)
919
{
920
struct capi_ctr *ctr;
921
u16 ret;
922
923
if (contr == 0) {
924
strlcpy(serial, driver_serial, CAPI_SERIAL_LEN);
925
return CAPI_NOERROR;
926
}
927
928
mutex_lock(&capi_controller_lock);
929
930
ctr = get_capi_ctr_by_nr(contr);
931
if (ctr && ctr->state == CAPI_CTR_RUNNING) {
932
strlcpy(serial, ctr->serial, CAPI_SERIAL_LEN);
933
ret = CAPI_NOERROR;
934
} else
935
ret = CAPI_REGNOTINSTALLED;
936
937
mutex_unlock(&capi_controller_lock);
938
return ret;
939
}
940
941
EXPORT_SYMBOL(capi20_get_serial);
942
943
/**
944
* capi20_get_profile() - CAPI 2.0 operation CAPI_GET_PROFILE
945
* @contr: controller number.
946
* @profp: result structure.
947
*
948
* Retrieve capability information for the specified ISDN controller
949
* or (for @contr == 0) the number of installed controllers.
950
* Return value: CAPI result code
951
*/
952
953
u16 capi20_get_profile(u32 contr, struct capi_profile *profp)
954
{
955
struct capi_ctr *ctr;
956
u16 ret;
957
958
if (contr == 0) {
959
profp->ncontroller = ncontrollers;
960
return CAPI_NOERROR;
961
}
962
963
mutex_lock(&capi_controller_lock);
964
965
ctr = get_capi_ctr_by_nr(contr);
966
if (ctr && ctr->state == CAPI_CTR_RUNNING) {
967
memcpy(profp, &ctr->profile, sizeof(struct capi_profile));
968
ret = CAPI_NOERROR;
969
} else
970
ret = CAPI_REGNOTINSTALLED;
971
972
mutex_unlock(&capi_controller_lock);
973
return ret;
974
}
975
976
EXPORT_SYMBOL(capi20_get_profile);
977
978
/* Must be called with capi_controller_lock held. */
979
static int wait_on_ctr_state(struct capi_ctr *ctr, unsigned int state)
980
{
981
DEFINE_WAIT(wait);
982
int retval = 0;
983
984
ctr = capi_ctr_get(ctr);
985
if (!ctr)
986
return -ESRCH;
987
988
for (;;) {
989
prepare_to_wait(&ctr->state_wait_queue, &wait,
990
TASK_INTERRUPTIBLE);
991
992
if (ctr->state == state)
993
break;
994
if (ctr->state == CAPI_CTR_DETACHED) {
995
retval = -ESRCH;
996
break;
997
}
998
if (signal_pending(current)) {
999
retval = -EINTR;
1000
break;
1001
}
1002
1003
mutex_unlock(&capi_controller_lock);
1004
schedule();
1005
mutex_lock(&capi_controller_lock);
1006
}
1007
finish_wait(&ctr->state_wait_queue, &wait);
1008
1009
capi_ctr_put(ctr);
1010
1011
return retval;
1012
}
1013
1014
#ifdef AVMB1_COMPAT
1015
static int old_capi_manufacturer(unsigned int cmd, void __user *data)
1016
{
1017
avmb1_loadandconfigdef ldef;
1018
avmb1_extcarddef cdef;
1019
avmb1_resetdef rdef;
1020
capicardparams cparams;
1021
struct capi_ctr *ctr;
1022
struct capi_driver *driver = NULL;
1023
capiloaddata ldata;
1024
struct list_head *l;
1025
int retval;
1026
1027
switch (cmd) {
1028
case AVMB1_ADDCARD:
1029
case AVMB1_ADDCARD_WITH_TYPE:
1030
if (cmd == AVMB1_ADDCARD) {
1031
if ((retval = copy_from_user(&cdef, data,
1032
sizeof(avmb1_carddef))))
1033
return -EFAULT;
1034
cdef.cardtype = AVM_CARDTYPE_B1;
1035
} else {
1036
if ((retval = copy_from_user(&cdef, data,
1037
sizeof(avmb1_extcarddef))))
1038
return -EFAULT;
1039
}
1040
cparams.port = cdef.port;
1041
cparams.irq = cdef.irq;
1042
cparams.cardnr = cdef.cardnr;
1043
1044
mutex_lock(&capi_drivers_lock);
1045
1046
switch (cdef.cardtype) {
1047
case AVM_CARDTYPE_B1:
1048
list_for_each(l, &capi_drivers) {
1049
driver = list_entry(l, struct capi_driver, list);
1050
if (strcmp(driver->name, "b1isa") == 0)
1051
break;
1052
}
1053
break;
1054
case AVM_CARDTYPE_T1:
1055
list_for_each(l, &capi_drivers) {
1056
driver = list_entry(l, struct capi_driver, list);
1057
if (strcmp(driver->name, "t1isa") == 0)
1058
break;
1059
}
1060
break;
1061
default:
1062
driver = NULL;
1063
break;
1064
}
1065
if (!driver) {
1066
printk(KERN_ERR "kcapi: driver not loaded.\n");
1067
retval = -EIO;
1068
} else if (!driver->add_card) {
1069
printk(KERN_ERR "kcapi: driver has no add card function.\n");
1070
retval = -EIO;
1071
} else
1072
retval = driver->add_card(driver, &cparams);
1073
1074
mutex_unlock(&capi_drivers_lock);
1075
return retval;
1076
1077
case AVMB1_LOAD:
1078
case AVMB1_LOAD_AND_CONFIG:
1079
1080
if (cmd == AVMB1_LOAD) {
1081
if (copy_from_user(&ldef, data,
1082
sizeof(avmb1_loaddef)))
1083
return -EFAULT;
1084
ldef.t4config.len = 0;
1085
ldef.t4config.data = NULL;
1086
} else {
1087
if (copy_from_user(&ldef, data,
1088
sizeof(avmb1_loadandconfigdef)))
1089
return -EFAULT;
1090
}
1091
1092
mutex_lock(&capi_controller_lock);
1093
1094
ctr = get_capi_ctr_by_nr(ldef.contr);
1095
if (!ctr) {
1096
retval = -EINVAL;
1097
goto load_unlock_out;
1098
}
1099
1100
if (ctr->load_firmware == NULL) {
1101
printk(KERN_DEBUG "kcapi: load: no load function\n");
1102
retval = -ESRCH;
1103
goto load_unlock_out;
1104
}
1105
1106
if (ldef.t4file.len <= 0) {
1107
printk(KERN_DEBUG "kcapi: load: invalid parameter: length of t4file is %d ?\n", ldef.t4file.len);
1108
retval = -EINVAL;
1109
goto load_unlock_out;
1110
}
1111
if (ldef.t4file.data == NULL) {
1112
printk(KERN_DEBUG "kcapi: load: invalid parameter: dataptr is 0\n");
1113
retval = -EINVAL;
1114
goto load_unlock_out;
1115
}
1116
1117
ldata.firmware.user = 1;
1118
ldata.firmware.data = ldef.t4file.data;
1119
ldata.firmware.len = ldef.t4file.len;
1120
ldata.configuration.user = 1;
1121
ldata.configuration.data = ldef.t4config.data;
1122
ldata.configuration.len = ldef.t4config.len;
1123
1124
if (ctr->state != CAPI_CTR_DETECTED) {
1125
printk(KERN_INFO "kcapi: load: contr=%d not in detect state\n", ldef.contr);
1126
retval = -EBUSY;
1127
goto load_unlock_out;
1128
}
1129
ctr->state = CAPI_CTR_LOADING;
1130
1131
retval = ctr->load_firmware(ctr, &ldata);
1132
if (retval) {
1133
ctr->state = CAPI_CTR_DETECTED;
1134
goto load_unlock_out;
1135
}
1136
1137
retval = wait_on_ctr_state(ctr, CAPI_CTR_RUNNING);
1138
1139
load_unlock_out:
1140
mutex_unlock(&capi_controller_lock);
1141
return retval;
1142
1143
case AVMB1_RESETCARD:
1144
if (copy_from_user(&rdef, data, sizeof(avmb1_resetdef)))
1145
return -EFAULT;
1146
1147
retval = 0;
1148
1149
mutex_lock(&capi_controller_lock);
1150
1151
ctr = get_capi_ctr_by_nr(rdef.contr);
1152
if (!ctr) {
1153
retval = -ESRCH;
1154
goto reset_unlock_out;
1155
}
1156
1157
if (ctr->state == CAPI_CTR_DETECTED)
1158
goto reset_unlock_out;
1159
1160
if (ctr->reset_ctr == NULL) {
1161
printk(KERN_DEBUG "kcapi: reset: no reset function\n");
1162
retval = -ESRCH;
1163
goto reset_unlock_out;
1164
}
1165
1166
ctr->reset_ctr(ctr);
1167
1168
retval = wait_on_ctr_state(ctr, CAPI_CTR_DETECTED);
1169
1170
reset_unlock_out:
1171
mutex_unlock(&capi_controller_lock);
1172
return retval;
1173
}
1174
return -EINVAL;
1175
}
1176
#endif
1177
1178
/**
1179
* capi20_manufacturer() - CAPI 2.0 operation CAPI_MANUFACTURER
1180
* @cmd: command.
1181
* @data: parameter.
1182
*
1183
* Perform manufacturer specific command.
1184
* Return value: CAPI result code
1185
*/
1186
1187
int capi20_manufacturer(unsigned int cmd, void __user *data)
1188
{
1189
struct capi_ctr *ctr;
1190
int retval;
1191
1192
switch (cmd) {
1193
#ifdef AVMB1_COMPAT
1194
case AVMB1_LOAD:
1195
case AVMB1_LOAD_AND_CONFIG:
1196
case AVMB1_RESETCARD:
1197
case AVMB1_GET_CARDINFO:
1198
case AVMB1_REMOVECARD:
1199
return old_capi_manufacturer(cmd, data);
1200
#endif
1201
case KCAPI_CMD_TRACE:
1202
{
1203
kcapi_flagdef fdef;
1204
1205
if (copy_from_user(&fdef, data, sizeof(kcapi_flagdef)))
1206
return -EFAULT;
1207
1208
mutex_lock(&capi_controller_lock);
1209
1210
ctr = get_capi_ctr_by_nr(fdef.contr);
1211
if (ctr) {
1212
ctr->traceflag = fdef.flag;
1213
printk(KERN_INFO "kcapi: contr [%03d] set trace=%d\n",
1214
ctr->cnr, ctr->traceflag);
1215
retval = 0;
1216
} else
1217
retval = -ESRCH;
1218
1219
mutex_unlock(&capi_controller_lock);
1220
1221
return retval;
1222
}
1223
case KCAPI_CMD_ADDCARD:
1224
{
1225
struct list_head *l;
1226
struct capi_driver *driver = NULL;
1227
capicardparams cparams;
1228
kcapi_carddef cdef;
1229
1230
if ((retval = copy_from_user(&cdef, data, sizeof(cdef))))
1231
return -EFAULT;
1232
1233
cparams.port = cdef.port;
1234
cparams.irq = cdef.irq;
1235
cparams.membase = cdef.membase;
1236
cparams.cardnr = cdef.cardnr;
1237
cparams.cardtype = 0;
1238
cdef.driver[sizeof(cdef.driver)-1] = 0;
1239
1240
mutex_lock(&capi_drivers_lock);
1241
1242
list_for_each(l, &capi_drivers) {
1243
driver = list_entry(l, struct capi_driver, list);
1244
if (strcmp(driver->name, cdef.driver) == 0)
1245
break;
1246
}
1247
if (driver == NULL) {
1248
printk(KERN_ERR "kcapi: driver \"%s\" not loaded.\n",
1249
cdef.driver);
1250
retval = -ESRCH;
1251
} else if (!driver->add_card) {
1252
printk(KERN_ERR "kcapi: driver \"%s\" has no add card function.\n", cdef.driver);
1253
retval = -EIO;
1254
} else
1255
retval = driver->add_card(driver, &cparams);
1256
1257
mutex_unlock(&capi_drivers_lock);
1258
return retval;
1259
}
1260
1261
default:
1262
printk(KERN_ERR "kcapi: manufacturer command %d unknown.\n",
1263
cmd);
1264
break;
1265
1266
}
1267
return -EINVAL;
1268
}
1269
1270
EXPORT_SYMBOL(capi20_manufacturer);
1271
1272
/* ------------------------------------------------------------- */
1273
/* -------- Init & Cleanup ------------------------------------- */
1274
/* ------------------------------------------------------------- */
1275
1276
/*
1277
* init / exit functions
1278
*/
1279
1280
static struct notifier_block capictr_nb = {
1281
.notifier_call = notify_handler,
1282
.priority = INT_MAX,
1283
};
1284
1285
static int __init kcapi_init(void)
1286
{
1287
int err;
1288
1289
kcapi_wq = alloc_workqueue("kcapi", 0, 0);
1290
if (!kcapi_wq)
1291
return -ENOMEM;
1292
1293
register_capictr_notifier(&capictr_nb);
1294
1295
err = cdebug_init();
1296
if (err) {
1297
unregister_capictr_notifier(&capictr_nb);
1298
destroy_workqueue(kcapi_wq);
1299
return err;
1300
}
1301
1302
kcapi_proc_init();
1303
return 0;
1304
}
1305
1306
static void __exit kcapi_exit(void)
1307
{
1308
kcapi_proc_exit();
1309
1310
unregister_capictr_notifier(&capictr_nb);
1311
cdebug_exit();
1312
destroy_workqueue(kcapi_wq);
1313
}
1314
1315
module_init(kcapi_init);
1316
module_exit(kcapi_exit);
1317
1318