2 * $Id: capiutil.c,v 1.9 1999/07/09 15:05:46 keil Exp $
4 * CAPI 2.0 convert capi message to capi message struct
6 * From CAPI 2.0 Development Kit AVM 1995 (msg.c)
7 * Rewritten for Linux 1996 by Carsten Paeth (calle@calle.in-berlin.de)
10 * Revision 1.9 1999/07/09 15:05:46 keil
11 * compat.h is now isdn_compat.h
13 * Revision 1.8 1999/07/01 15:26:37 calle
14 * complete new version (I love it):
15 * + new hardware independed "capi_driver" interface that will make it easy to:
16 * - support other controllers with CAPI-2.0 (i.e. USB Controller)
17 * - write a CAPI-2.0 for the passive cards
18 * - support serial link CAPI-2.0 boxes.
19 * + wrote "capi_driver" for all supported cards.
20 * + "capi_driver" (supported cards) now have to be configured with
21 * make menuconfig, in the past all supported cards where included
23 * + new and better informations in /proc/capi/
24 * + new ioctl to switch trace of capi messages per controller
25 * using "avmcapictrl trace [contr] on|off|...."
26 * + complete testcircle with all supported cards and also the
27 * PCMCIA cards (now patch for pcmcia-cs-3.0.13 needed) done.
29 * Revision 1.7 1999/07/01 08:23:01 keil
30 * compatibility macros now in <linux/isdn_compat.h>
32 * Revision 1.6 1997/11/04 06:12:12 calle
33 * capi.c: new read/write in file_ops since 2.1.60
34 * capidrv.c: prepared isdnlog interface for d2-trace in newer firmware.
35 * capiutil.c: needs config.h (CONFIG_ISDN_DRV_AVMB1_VERBOSE_REASON)
36 * compat.h: added #define LinuxVersionCode
38 * Revision 1.5 1997/10/01 09:21:19 fritz
39 * Removed old compatibility stuff for 2.0.X kernels.
40 * From now on, this code is for 2.1.X ONLY!
41 * Old stuff is still in the separate branch.
43 * Revision 1.4 1997/08/10 07:43:55 calle
44 * forgot to export symbol capi_info2str for 2.1.x
46 * Revision 1.3 1997/05/18 09:24:18 calle
47 * added verbose disconnect reason reporting to avmb1.
48 * some fixes in capi20 interface.
49 * changed info messages for B1-PCI
51 * Revision 1.2 1997/03/05 21:22:13 fritz
52 * Fix: Symbols have to be exported unconditionally.
54 * Revision 1.1 1997/03/04 21:50:34 calle
55 * Frirst version in isdn4linux
57 * Revision 2.2 1997/02/12 09:31:39 calle
60 * Revision 1.1 1997/01/31 10:32:20 calle
64 #include <linux/module.h>
65 #include <linux/string.h>
66 #include <linux/ctype.h>
67 #include <linux/stddef.h>
68 #include <linux/kernel.h>
70 #include <asm/segment.h>
71 #include <linux/config.h>
73 #include <linux/isdn_compat.h>
76 /* from CAPI2.0 DDK AVM Berlin GmbH */
78 #ifndef CONFIG_ISDN_DRV_AVMB1_VERBOSE_REASON
79 char *capi_info2str(__u16 reason
)
84 char *capi_info2str(__u16 reason
)
88 /*-- informative values (corresponding message was processed) -----*/
90 return "NCPI not supported by current protocol, NCPI ignored";
92 return "Flags not supported by current protocol, flags ignored";
94 return "Alert already sent by another application";
96 /*-- error information concerning CAPI_REGISTER -----*/
98 return "Too many applications";
100 return "Logical block size to small, must be at least 128 Bytes";
102 return "Buffer exceeds 64 kByte";
104 return "Message buffer size too small, must be at least 1024 Bytes";
106 return "Max. number of logical connections not supported";
110 return "The message could not be accepted because of an internal busy condition";
112 return "OS resource error (no memory ?)";
114 return "CAPI not installed";
116 return "Controller does not support external equipment";
118 return "Controller does only support external equipment";
120 /*-- error information concerning message exchange functions -----*/
122 return "Illegal application number";
124 return "Illegal command or subcommand or message length less than 12 bytes";
126 return "The message could not be accepted because of a queue full condition !! The error code does not imply that CAPI cannot receive messages directed to another controller, PLCI or NCCI";
128 return "Queue is empty";
130 return "Queue overflow, a message was lost !! This indicates a configuration error. The only recovery from this error is to perform a CAPI_RELEASE";
132 return "Unknown notification parameter";
134 return "The Message could not be accepted because of an internal busy condition";
136 return "OS Resource error (no memory ?)";
138 return "CAPI not installed";
140 return "Controller does not support external equipment";
142 return "Controller does only support external equipment";
144 /*-- error information concerning resource / coding problems -----*/
146 return "Message not supported in current state";
148 return "Illegal Controller / PLCI / NCCI";
150 return "Out of PLCI";
152 return "Out of NCCI";
154 return "Out of LISTEN";
156 return "Out of FAX resources (protocol T.30)";
158 return "Illegal message parameter coding";
160 /*-- error information concerning requested services -----*/
162 return "B1 protocol not supported";
164 return "B2 protocol not supported";
166 return "B3 protocol not supported";
168 return "B1 protocol parameter not supported";
170 return "B2 protocol parameter not supported";
172 return "B3 protocol parameter not supported";
174 return "B protocol combination not supported";
176 return "NCPI not supported";
178 return "CIP Value unknown";
180 return "Flags not supported (reserved bits)";
182 return "Facility not supported";
184 return "Data length not supported by current protocol";
186 return "Reset procedure not supported by current protocol";
188 /*-- informations about the clearing of a physical connection -----*/
190 return "Protocol error layer 1 (broken line or B-channel removed by signalling protocol)";
192 return "Protocol error layer 2";
194 return "Protocol error layer 3";
196 return "Another application got that call";
197 /*-- T.30 specific reasons -----*/
199 return "Connecting not successful (remote station is no FAX G3 machine)";
201 return "Connecting not successful (training error)";
203 return "Disconnected before transfer (remote station does not support transfer mode, e.g. resolution)";
205 return "Disconnected during transfer (remote abort)";
207 return "Disconnected during transfer (remote procedure error, e.g. unsuccessful repetition of T.30 commands)";
209 return "Disconnected during transfer (local tx data underrun)";
211 return "Disconnected during transfer (local rx data overflow)";
213 return "Disconnected during transfer (local abort)";
215 return "Illegal parameter coding (e.g. SFF coding error)";
217 /*-- disconnect causes from the network according to ETS 300 102-1/Q.931 -----*/
218 case 0x3481: return "Unallocated (unassigned) number";
219 case 0x3482: return "No route to specified transit network";
220 case 0x3483: return "No route to destination";
221 case 0x3486: return "Channel unacceptable";
223 return "Call awarded and being delivered in an established channel";
224 case 0x3490: return "Normal call clearing";
225 case 0x3491: return "User busy";
226 case 0x3492: return "No user responding";
227 case 0x3493: return "No answer from user (user alerted)";
228 case 0x3495: return "Call rejected";
229 case 0x3496: return "Number changed";
230 case 0x349A: return "Non-selected user clearing";
231 case 0x349B: return "Destination out of order";
232 case 0x349C: return "Invalid number format";
233 case 0x349D: return "Facility rejected";
234 case 0x349E: return "Response to STATUS ENQUIRY";
235 case 0x349F: return "Normal, unspecified";
236 case 0x34A2: return "No circuit / channel available";
237 case 0x34A6: return "Network out of order";
238 case 0x34A9: return "Temporary failure";
239 case 0x34AA: return "Switching equipment congestion";
240 case 0x34AB: return "Access information discarded";
241 case 0x34AC: return "Requested circuit / channel not available";
242 case 0x34AF: return "Resources unavailable, unspecified";
243 case 0x34B1: return "Quality of service unavailable";
244 case 0x34B2: return "Requested facility not subscribed";
245 case 0x34B9: return "Bearer capability not authorized";
246 case 0x34BA: return "Bearer capability not presently available";
247 case 0x34BF: return "Service or option not available, unspecified";
248 case 0x34C1: return "Bearer capability not implemented";
249 case 0x34C2: return "Channel type not implemented";
250 case 0x34C5: return "Requested facility not implemented";
251 case 0x34C6: return "Only restricted digital information bearer capability is available";
252 case 0x34CF: return "Service or option not implemented, unspecified";
253 case 0x34D1: return "Invalid call reference value";
254 case 0x34D2: return "Identified channel does not exist";
255 case 0x34D3: return "A suspended call exists, but this call identity does not";
256 case 0x34D4: return "Call identity in use";
257 case 0x34D5: return "No call suspended";
258 case 0x34D6: return "Call having the requested call identity has been cleared";
259 case 0x34D8: return "Incompatible destination";
260 case 0x34DB: return "Invalid transit network selection";
261 case 0x34DF: return "Invalid message, unspecified";
262 case 0x34E0: return "Mandatory information element is missing";
263 case 0x34E1: return "Message type non-existent or not implemented";
264 case 0x34E2: return "Message not compatible with call state or message type non-existent or not implemented";
265 case 0x34E3: return "Information element non-existent or not implemented";
266 case 0x34E4: return "Invalid information element contents";
267 case 0x34E5: return "Message not compatible with call state";
268 case 0x34E6: return "Recovery on timer expiry";
269 case 0x34EF: return "Protocol error, unspecified";
270 case 0x34FF: return "Interworking, unspecified";
272 default: return "No additional information";
289 static _cdef cdef
[] =
298 {_CDWORD
, offsetof(_cmsg
, adr
.adrController
)},
300 {_CMSTRUCT
, offsetof(_cmsg
, AdditionalInfo
)},
302 {_CSTRUCT
, offsetof(_cmsg
, B1configuration
)},
304 {_CWORD
, offsetof(_cmsg
, B1protocol
)},
306 {_CSTRUCT
, offsetof(_cmsg
, B2configuration
)},
308 {_CWORD
, offsetof(_cmsg
, B2protocol
)},
310 {_CSTRUCT
, offsetof(_cmsg
, B3configuration
)},
312 {_CWORD
, offsetof(_cmsg
, B3protocol
)},
314 {_CSTRUCT
, offsetof(_cmsg
, BC
)},
316 {_CSTRUCT
, offsetof(_cmsg
, BChannelinformation
)},
318 {_CMSTRUCT
, offsetof(_cmsg
, BProtocol
)},
320 {_CSTRUCT
, offsetof(_cmsg
, CalledPartyNumber
)},
322 {_CSTRUCT
, offsetof(_cmsg
, CalledPartySubaddress
)},
324 {_CSTRUCT
, offsetof(_cmsg
, CallingPartyNumber
)},
326 {_CSTRUCT
, offsetof(_cmsg
, CallingPartySubaddress
)},
328 {_CDWORD
, offsetof(_cmsg
, CIPmask
)},
330 {_CDWORD
, offsetof(_cmsg
, CIPmask2
)},
332 {_CWORD
, offsetof(_cmsg
, CIPValue
)},
334 {_CDWORD
, offsetof(_cmsg
, Class
)},
336 {_CSTRUCT
, offsetof(_cmsg
, ConnectedNumber
)},
338 {_CSTRUCT
, offsetof(_cmsg
, ConnectedSubaddress
)},
340 {_CDWORD
, offsetof(_cmsg
, Data
)},
342 {_CWORD
, offsetof(_cmsg
, DataHandle
)},
344 {_CWORD
, offsetof(_cmsg
, DataLength
)},
346 {_CSTRUCT
, offsetof(_cmsg
, FacilityConfirmationParameter
)},
348 {_CSTRUCT
, offsetof(_cmsg
, Facilitydataarray
)},
350 {_CSTRUCT
, offsetof(_cmsg
, FacilityIndicationParameter
)},
352 {_CSTRUCT
, offsetof(_cmsg
, FacilityRequestParameter
)},
354 {_CWORD
, offsetof(_cmsg
, FacilitySelector
)},
356 {_CWORD
, offsetof(_cmsg
, Flags
)},
358 {_CDWORD
, offsetof(_cmsg
, Function
)},
360 {_CSTRUCT
, offsetof(_cmsg
, HLC
)},
362 {_CWORD
, offsetof(_cmsg
, Info
)},
364 {_CSTRUCT
, offsetof(_cmsg
, InfoElement
)},
366 {_CDWORD
, offsetof(_cmsg
, InfoMask
)},
368 {_CWORD
, offsetof(_cmsg
, InfoNumber
)},
370 {_CSTRUCT
, offsetof(_cmsg
, Keypadfacility
)},
372 {_CSTRUCT
, offsetof(_cmsg
, LLC
)},
374 {_CSTRUCT
, offsetof(_cmsg
, ManuData
)},
376 {_CDWORD
, offsetof(_cmsg
, ManuID
)},
378 {_CSTRUCT
, offsetof(_cmsg
, NCPI
)},
380 {_CWORD
, offsetof(_cmsg
, Reason
)},
382 {_CWORD
, offsetof(_cmsg
, Reason_B3
)},
384 {_CWORD
, offsetof(_cmsg
, Reject
)},
386 {_CSTRUCT
, offsetof(_cmsg
, Useruserdata
)}
389 static unsigned char *cpars
[] =
392 /*01 ALERT_REQ */ (unsigned char *) "\x03\x04\x0c\x27\x2f\x1c\x01\x01",
393 /*02 CONNECT_REQ */ (unsigned char *) "\x03\x14\x0e\x10\x0f\x11\x0d\x06\x08\x0a\x05\x07\x09\x01\x0b\x28\x22\x04\x0c\x27\x2f\x1c\x01\x01",
395 /*04 DISCONNECT_REQ */ (unsigned char *) "\x03\x04\x0c\x27\x2f\x1c\x01\x01",
396 /*05 LISTEN_REQ */ (unsigned char *) "\x03\x25\x12\x13\x10\x11\x01",
399 /*08 INFO_REQ */ (unsigned char *) "\x03\x0e\x04\x0c\x27\x2f\x1c\x01\x01",
400 /*09 FACILITY_REQ */ (unsigned char *) "\x03\x1f\x1e\x01",
401 /*0a SELECT_B_PROTOCOL_REQ */ (unsigned char *) "\x03\x0d\x06\x08\x0a\x05\x07\x09\x01\x01",
402 /*0b CONNECT_B3_REQ */ (unsigned char *) "\x03\x2b\x01",
404 /*0d DISCONNECT_B3_REQ */ (unsigned char *) "\x03\x2b\x01",
406 /*0f DATA_B3_REQ */ (unsigned char *) "\x03\x18\x1a\x19\x20\x01",
407 /*10 RESET_B3_REQ */ (unsigned char *) "\x03\x2b\x01",
410 /*13 ALERT_CONF */ (unsigned char *) "\x03\x23\x01",
411 /*14 CONNECT_CONF */ (unsigned char *) "\x03\x23\x01",
413 /*16 DISCONNECT_CONF */ (unsigned char *) "\x03\x23\x01",
414 /*17 LISTEN_CONF */ (unsigned char *) "\x03\x23\x01",
415 /*18 MANUFACTURER_REQ */ (unsigned char *) "\x03\x2a\x15\x21\x29\x01",
417 /*1a INFO_CONF */ (unsigned char *) "\x03\x23\x01",
418 /*1b FACILITY_CONF */ (unsigned char *) "\x03\x23\x1f\x1b\x01",
419 /*1c SELECT_B_PROTOCOL_CONF */ (unsigned char *) "\x03\x23\x01",
420 /*1d CONNECT_B3_CONF */ (unsigned char *) "\x03\x23\x01",
422 /*1f DISCONNECT_B3_CONF */ (unsigned char *) "\x03\x23\x01",
424 /*21 DATA_B3_CONF */ (unsigned char *) "\x03\x19\x23\x01",
425 /*22 RESET_B3_CONF */ (unsigned char *) "\x03\x23\x01",
429 /*26 CONNECT_IND */ (unsigned char *) "\x03\x14\x0e\x10\x0f\x11\x0b\x28\x22\x04\x0c\x27\x2f\x1c\x01\x01",
430 /*27 CONNECT_ACTIVE_IND */ (unsigned char *) "\x03\x16\x17\x28\x01",
431 /*28 DISCONNECT_IND */ (unsigned char *) "\x03\x2c\x01",
433 /*2a MANUFACTURER_CONF */ (unsigned char *) "\x03\x2a\x15\x21\x29\x01",
435 /*2c INFO_IND */ (unsigned char *) "\x03\x26\x24\x01",
436 /*2d FACILITY_IND */ (unsigned char *) "\x03\x1f\x1d\x01",
438 /*2f CONNECT_B3_IND */ (unsigned char *) "\x03\x2b\x01",
439 /*30 CONNECT_B3_ACTIVE_IND */ (unsigned char *) "\x03\x2b\x01",
440 /*31 DISCONNECT_B3_IND */ (unsigned char *) "\x03\x2d\x2b\x01",
442 /*33 DATA_B3_IND */ (unsigned char *) "\x03\x18\x1a\x19\x20\x01",
443 /*34 RESET_B3_IND */ (unsigned char *) "\x03\x2b\x01",
444 /*35 CONNECT_B3_T90_ACTIVE_IND */ (unsigned char *) "\x03\x2b\x01",
447 /*38 CONNECT_RESP */ (unsigned char *) "\x03\x2e\x0d\x06\x08\x0a\x05\x07\x09\x01\x16\x17\x28\x04\x0c\x27\x2f\x1c\x01\x01",
448 /*39 CONNECT_ACTIVE_RESP */ (unsigned char *) "\x03\x01",
449 /*3a DISCONNECT_RESP */ (unsigned char *) "\x03\x01",
451 /*3c MANUFACTURER_IND */ (unsigned char *) "\x03\x2a\x15\x21\x29\x01",
453 /*3e INFO_RESP */ (unsigned char *) "\x03\x01",
454 /*3f FACILITY_RESP */ (unsigned char *) "\x03\x1f\x01",
456 /*41 CONNECT_B3_RESP */ (unsigned char *) "\x03\x2e\x2b\x01",
457 /*42 CONNECT_B3_ACTIVE_RESP */ (unsigned char *) "\x03\x01",
458 /*43 DISCONNECT_B3_RESP */ (unsigned char *) "\x03\x01",
460 /*45 DATA_B3_RESP */ (unsigned char *) "\x03\x19\x01",
461 /*46 RESET_B3_RESP */ (unsigned char *) "\x03\x01",
462 /*47 CONNECT_B3_T90_ACTIVE_RESP */ (unsigned char *) "\x03\x01",
469 /*4e MANUFACTURER_RESP */ (unsigned char *) "\x03\x2a\x15\x21\x29\x01",
472 /*-------------------------------------------------------*/
474 #define byteTLcpy(x,y) *(__u8 *)(x)=*(__u8 *)(y);
475 #define wordTLcpy(x,y) *(__u16 *)(x)=*(__u16 *)(y);
476 #define dwordTLcpy(x,y) memcpy(x,y,4);
477 #define structTLcpy(x,y,l) memcpy (x,y,l)
478 #define structTLcpyovl(x,y,l) memmove (x,y,l)
480 #define byteTRcpy(x,y) *(__u8 *)(y)=*(__u8 *)(x);
481 #define wordTRcpy(x,y) *(__u16 *)(y)=*(__u16 *)(x);
482 #define dwordTRcpy(x,y) memcpy(y,x,4);
483 #define structTRcpy(x,y,l) memcpy (y,x,l)
484 #define structTRcpyovl(x,y,l) memmove (y,x,l)
486 /*-------------------------------------------------------*/
487 static unsigned command_2_index(unsigned c
, unsigned sc
)
490 c
= 0x9 + (c
& 0x0f);
496 return (sc
& 3) * (0x9 + 0x9) + c
;
499 /*-------------------------------------------------------*/
500 #define TYP (cdef[cmsg->par[cmsg->p]].typ)
501 #define OFF (((__u8 *)cmsg)+cdef[cmsg->par[cmsg->p]].off)
503 static void jumpcstruct(_cmsg
* cmsg
)
506 for (cmsg
->p
++, layer
= 1; layer
;) {
507 /* $$$$$ assert (cmsg->p); */
519 /*-------------------------------------------------------*/
520 static void pars_2_message(_cmsg
* cmsg
)
523 for (; TYP
!= _CEND
; cmsg
->p
++) {
526 byteTLcpy(cmsg
->m
+ cmsg
->l
, OFF
);
530 wordTLcpy(cmsg
->m
+ cmsg
->l
, OFF
);
534 dwordTLcpy(cmsg
->m
+ cmsg
->l
, OFF
);
538 if (*(__u8
**) OFF
== 0) {
539 *(cmsg
->m
+ cmsg
->l
) = '\0';
541 } else if (**(_cstruct
*) OFF
!= 0xff) {
542 structTLcpy(cmsg
->m
+ cmsg
->l
, *(_cstruct
*) OFF
, 1 + **(_cstruct
*) OFF
);
543 cmsg
->l
+= 1 + **(_cstruct
*) OFF
;
545 _cstruct s
= *(_cstruct
*) OFF
;
546 structTLcpy(cmsg
->m
+ cmsg
->l
, s
, 3 + *(__u16
*) (s
+ 1));
547 cmsg
->l
+= 3 + *(__u16
*) (s
+ 1);
551 /*----- Metastruktur 0 -----*/
552 if (*(_cmstruct
*) OFF
== CAPI_DEFAULT
) {
553 *(cmsg
->m
+ cmsg
->l
) = '\0';
557 /*----- Metastruktur wird composed -----*/
559 unsigned _l
= cmsg
->l
;
563 pars_2_message(cmsg
);
564 _ls
= cmsg
->l
- _l
- 1;
566 (cmsg
->m
+ _l
)[0] = (__u8
) _ls
;
568 structTLcpyovl(cmsg
->m
+ _l
+ 3, cmsg
->m
+ _l
+ 1, _ls
);
569 (cmsg
->m
+ _l
)[0] = 0xff;
570 wordTLcpy(cmsg
->m
+ _l
+ 1, &_ls
);
578 /*-------------------------------------------------------*/
579 unsigned capi_cmsg2message(_cmsg
* cmsg
, __u8
* msg
)
584 cmsg
->par
= cpars
[command_2_index(cmsg
->Command
, cmsg
->Subcommand
)];
586 pars_2_message(cmsg
);
588 wordTLcpy(msg
+ 0, &cmsg
->l
);
589 byteTLcpy(cmsg
->m
+ 4, &cmsg
->Command
);
590 byteTLcpy(cmsg
->m
+ 5, &cmsg
->Subcommand
);
591 wordTLcpy(cmsg
->m
+ 2, &cmsg
->ApplId
);
592 wordTLcpy(cmsg
->m
+ 6, &cmsg
->Messagenumber
);
597 /*-------------------------------------------------------*/
598 static void message_2_pars(_cmsg
* cmsg
)
600 for (; TYP
!= _CEND
; cmsg
->p
++) {
604 byteTRcpy(cmsg
->m
+ cmsg
->l
, OFF
);
608 wordTRcpy(cmsg
->m
+ cmsg
->l
, OFF
);
612 dwordTRcpy(cmsg
->m
+ cmsg
->l
, OFF
);
616 *(__u8
**) OFF
= cmsg
->m
+ cmsg
->l
;
618 if (cmsg
->m
[cmsg
->l
] != 0xff)
619 cmsg
->l
+= 1 + cmsg
->m
[cmsg
->l
];
621 cmsg
->l
+= 3 + *(__u16
*) (cmsg
->m
+ cmsg
->l
+ 1);
624 /*----- Metastruktur 0 -----*/
625 if (cmsg
->m
[cmsg
->l
] == '\0') {
626 *(_cmstruct
*) OFF
= CAPI_DEFAULT
;
630 unsigned _l
= cmsg
->l
;
631 *(_cmstruct
*) OFF
= CAPI_COMPOSE
;
632 cmsg
->l
= (cmsg
->m
+ _l
)[0] == 255 ? cmsg
->l
+ 3 : cmsg
->l
+ 1;
634 message_2_pars(cmsg
);
641 /*-------------------------------------------------------*/
642 unsigned capi_message2cmsg(_cmsg
* cmsg
, __u8
* msg
)
644 memset(cmsg
, 0, sizeof(_cmsg
));
648 byteTRcpy(cmsg
->m
+ 4, &cmsg
->Command
);
649 byteTRcpy(cmsg
->m
+ 5, &cmsg
->Subcommand
);
650 cmsg
->par
= cpars
[command_2_index(cmsg
->Command
, cmsg
->Subcommand
)];
652 message_2_pars(cmsg
);
654 wordTRcpy(msg
+ 0, &cmsg
->l
);
655 wordTRcpy(cmsg
->m
+ 2, &cmsg
->ApplId
);
656 wordTRcpy(cmsg
->m
+ 6, &cmsg
->Messagenumber
);
661 /*-------------------------------------------------------*/
662 unsigned capi_cmsg_header(_cmsg
* cmsg
, __u16 _ApplId
,
663 __u8 _Command
, __u8 _Subcommand
,
664 __u16 _Messagenumber
, __u32 _Controller
)
666 memset(cmsg
, 0, sizeof(_cmsg
));
667 cmsg
->ApplId
= _ApplId
;
668 cmsg
->Command
= _Command
;
669 cmsg
->Subcommand
= _Subcommand
;
670 cmsg
->Messagenumber
= _Messagenumber
;
671 cmsg
->adr
.adrController
= _Controller
;
675 /*-------------------------------------------------------*/
677 static char *mnames
[] =
689 "SELECT_B_PROTOCOL_REQ",
707 "SELECT_B_PROTOCOL_CONF",
710 "DISCONNECT_B3_CONF",
718 "CONNECT_ACTIVE_IND",
727 "CONNECT_B3_ACTIVE_IND",
732 "CONNECT_B3_T90_ACTIVE_IND",
736 "CONNECT_ACTIVE_RESP",
745 "CONNECT_B3_ACTIVE_RESP",
746 "DISCONNECT_B3_RESP",
750 "CONNECT_B3_T90_ACTIVE_RESP",
760 char *capi_cmd2str(__u8 cmd
, __u8 subcmd
)
762 return mnames
[command_2_index(cmd
, subcmd
)];
766 /*-------------------------------------------------------*/
767 /*-------------------------------------------------------*/
769 static char *pnames
[] =
774 /*03 */ "Controller/PLCI/NCCI",
775 /*04 */ "AdditionalInfo",
776 /*05 */ "B1configuration",
777 /*06 */ "B1protocol",
778 /*07 */ "B2configuration",
779 /*08 */ "B2protocol",
780 /*09 */ "B3configuration",
781 /*0a */ "B3protocol",
783 /*0c */ "BChannelinformation",
785 /*0e */ "CalledPartyNumber",
786 /*0f */ "CalledPartySubaddress",
787 /*10 */ "CallingPartyNumber",
788 /*11 */ "CallingPartySubaddress",
793 /*16 */ "ConnectedNumber",
794 /*17 */ "ConnectedSubaddress",
796 /*19 */ "DataHandle",
797 /*1a */ "DataLength",
798 /*1b */ "FacilityConfirmationParameter",
799 /*1c */ "Facilitydataarray",
800 /*1d */ "FacilityIndicationParameter",
801 /*1e */ "FacilityRequestParameter",
802 /*1f */ "FacilitySelector",
807 /*24 */ "InfoElement",
809 /*26 */ "InfoNumber",
810 /*27 */ "Keypadfacility",
818 /*2f */ "Useruserdata"
822 static char buf
[8192];
827 /*-------------------------------------------------------*/
828 static void bufprint(char *fmt
,...)
837 static void printstructlen(__u8
* m
, unsigned len
)
840 for (; len
; len
--, m
++)
841 if (isalnum(*m
) || *m
== ' ') {
848 bufprint("<%02x", *m
);
850 bufprint(" %02x", *m
);
857 static void printstruct(__u8
* m
)
864 len
= ((__u16
*) (m
+ 1))[0];
867 printstructlen(m
, len
);
870 /*-------------------------------------------------------*/
871 #define NAME (pnames[cmsg->par[cmsg->p]])
873 static void protocol_message_2_pars(_cmsg
* cmsg
, int level
)
875 for (; TYP
!= _CEND
; cmsg
->p
++) {
876 int slen
= 29 + 3 - level
;
880 for (i
= 0; i
< level
- 1; i
++)
885 bufprint("%-*s = 0x%x\n", slen
, NAME
, *(__u8
*) (cmsg
->m
+ cmsg
->l
));
889 bufprint("%-*s = 0x%x\n", slen
, NAME
, *(__u16
*) (cmsg
->m
+ cmsg
->l
));
893 if (strcmp(NAME
, "Data") == 0) {
894 bufprint("%-*s = ", slen
, NAME
);
895 printstructlen((__u8
*) * (__u32
*) (cmsg
->m
+ cmsg
->l
),
896 *(__u16
*) (cmsg
->m
+ cmsg
->l
+ sizeof(__u32
)));
899 bufprint("%-*s = 0x%lx\n", slen
, NAME
, *(__u32
*) (cmsg
->m
+ cmsg
->l
));
903 bufprint("%-*s = ", slen
, NAME
);
904 if (cmsg
->m
[cmsg
->l
] == '\0')
907 printstruct(cmsg
->m
+ cmsg
->l
);
909 if (cmsg
->m
[cmsg
->l
] != 0xff)
910 cmsg
->l
+= 1 + cmsg
->m
[cmsg
->l
];
912 cmsg
->l
+= 3 + *(__u16
*) (cmsg
->m
+ cmsg
->l
+ 1);
917 /*----- Metastruktur 0 -----*/
918 if (cmsg
->m
[cmsg
->l
] == '\0') {
919 bufprint("%-*s = default\n", slen
, NAME
);
924 unsigned _l
= cmsg
->l
;
925 bufprint("%-*s\n", slen
, name
);
926 cmsg
->l
= (cmsg
->m
+ _l
)[0] == 255 ? cmsg
->l
+ 3 : cmsg
->l
+ 1;
928 protocol_message_2_pars(cmsg
, level
+ 1);
934 /*-------------------------------------------------------*/
935 char *capi_message2str(__u8
* msg
)
945 byteTRcpy(cmsg
.m
+ 4, &cmsg
.Command
);
946 byteTRcpy(cmsg
.m
+ 5, &cmsg
.Subcommand
);
947 cmsg
.par
= cpars
[command_2_index(cmsg
.Command
, cmsg
.Subcommand
)];
949 bufprint("%-26s ID=%03d #0x%04x LEN=%04d\n",
950 mnames
[command_2_index(cmsg
.Command
, cmsg
.Subcommand
)],
951 ((unsigned short *) msg
)[1],
952 ((unsigned short *) msg
)[3],
953 ((unsigned short *) msg
)[0]);
955 protocol_message_2_pars(&cmsg
, 1);
959 char *capi_cmsg2str(_cmsg
* cmsg
)
965 bufprint("%s ID=%03d #0x%04x LEN=%04d\n",
966 mnames
[command_2_index(cmsg
->Command
, cmsg
->Subcommand
)],
967 ((__u16
*) cmsg
->m
)[1],
968 ((__u16
*) cmsg
->m
)[3],
969 ((__u16
*) cmsg
->m
)[0]);
970 protocol_message_2_pars(cmsg
, 1);
975 EXPORT_SYMBOL(capi_cmsg2message
);
976 EXPORT_SYMBOL(capi_message2cmsg
);
977 EXPORT_SYMBOL(capi_cmsg_header
);
978 EXPORT_SYMBOL(capi_cmd2str
);
979 EXPORT_SYMBOL(capi_cmsg2str
);
980 EXPORT_SYMBOL(capi_message2str
);
981 EXPORT_SYMBOL(capi_info2str
);
985 int init_module(void)
990 void cleanup_module(void)