提交 9c3c0c20 编写于 作者: A Arnd Bergmann

isdn: remove isdn4linux

With all isdn4linux hardware drivers gone, this is only a wrapper around
CAPI to support old user space. However, from looking at the mailing
list, it seems that the last time anyone asked about it was in 2014,
when the upgrade from a linux-2.4 installation failed, and mISDN was
suggested as a replacement.

The largest public ISDN network (Deutsche Telekom) was supposed to be
shut down 2018, which must have drastically reduced the number of legacy
installations.

When we last discussed removing i4l in 2016, Karsten Keil suggested
revisiting this in 2018. I guess this is overdue.

Link: http://listserv.isdn4linux.de/pipermail/isdn4linux/2014-October/006165.html
Link: https://patchwork.kernel.org/patch/8484861/#17900371
Link: https://listserv.isdn4linux.de/pipermail/isdn4linux/2019-April/thread.htmlSigned-off-by: NArnd Bergmann <arnd@arndb.de>
上级 85993b8c
此差异已折叠。
$Id: INTERFACE.fax,v 1.2 2000/08/06 09:22:50 armin Exp $
Description of the fax-subinterface between linklevel and hardwarelevel of
isdn4linux.
The communication between linklevel (LL) and hardwarelevel (HL) for fax
is based on the struct T30_s (defined in isdnif.h).
This struct is allocated in the LL.
In order to use fax, the LL provides the pointer to this struct with the
command ISDN_CMD_SETL3 (parm.fax). This pointer expires in case of hangup
and when a new channel to a new connection is assigned.
Data handling:
In send-mode the HL-driver has to handle the <DLE> codes and the bit-order
conversion by itself.
In receive-mode the LL-driver takes care of the bit-order conversion
(specified by +FBOR)
Structure T30_s description:
This structure stores the values (set by AT-commands), the remote-
capability-values and the command-codes between LL and HL.
If the HL-driver receives ISDN_CMD_FAXCMD, all needed information
is in this struct set by the LL.
To signal information to the LL, the HL-driver has to set the
parameters and use ISDN_STAT_FAXIND.
(Please refer to INTERFACE)
Structure T30_s:
All members are 8-bit unsigned (__u8)
- resolution
- rate
- width
- length
- compression
- ecm
- binary
- scantime
- id[]
Local faxmachine's parameters, set by +FDIS, +FDCS, +FLID, ...
- r_resolution
- r_rate
- r_width
- r_length
- r_compression
- r_ecm
- r_binary
- r_scantime
- r_id[]
Remote faxmachine's parameters. To be set by HL-driver.
- phase
Defines the actual state of fax connection. Set by HL or LL
depending on progress and type of connection.
If the phase changes because of an AT command, the LL driver
changes this value. Otherwise the HL-driver takes care of it, but
only necessary on call establishment (from IDLE to PHASE_A).
(one of the constants ISDN_FAX_PHASE_[IDLE,A,B,C,D,E])
- direction
Defines outgoing/send or incoming/receive connection.
(ISDN_TTY_FAX_CONN_[IN,OUT])
- code
Commands from LL to HL; possible constants :
ISDN_TTY_FAX_DR signals +FDR command to HL
ISDN_TTY_FAX_DT signals +FDT command to HL
ISDN_TTY_FAX_ET signals +FET command to HL
Other than that the "code" is set with the hangup-code value at
the end of connection for the +FHNG message.
- r_code
Commands from HL to LL; possible constants :
ISDN_TTY_FAX_CFR output of +FCFR message.
ISDN_TTY_FAX_RID output of remote ID set in r_id[]
(+FCSI/+FTSI on send/receive)
ISDN_TTY_FAX_DCS output of +FDCS and CONNECT message,
switching to phase C.
ISDN_TTY_FAX_ET signals end of data,
switching to phase D.
ISDN_TTY_FAX_FCON signals the established, outgoing connection,
switching to phase B.
ISDN_TTY_FAX_FCON_I signals the established, incoming connection,
switching to phase B.
ISDN_TTY_FAX_DIS output of +FDIS message and values.
ISDN_TTY_FAX_SENT signals that all data has been sent
and <DLE><ETX> is acknowledged,
OK message will be sent.
ISDN_TTY_FAX_PTS signals a msg-confirmation (page sent successful),
depending on fet value:
0: output OK message (more pages follow)
1: switching to phase B (next document)
ISDN_TTY_FAX_TRAIN_OK output of +FDCS and OK message (for receive mode).
ISDN_TTY_FAX_EOP signals end of data in receive mode,
switching to phase D.
ISDN_TTY_FAX_HNG output of the +FHNG and value set by code and
OK message, switching to phase E.
- badlin
Value of +FBADLIN
- badmul
Value of +FBADMUL
- bor
Value of +FBOR
- fet
Value of +FET command in send-mode.
Set by HL in receive-mode for +FET message.
- pollid[]
ID-string, set by +FCIG
- cq
Value of +FCQ
- cr
Value of +FCR
- ctcrty
Value of +FCTCRTY
- minsp
Value of +FMINSP
- phcto
Value of +FPHCTO
- rel
Value of +FREL
- nbc
Value of +FNBC (0,1)
(+FNBC is not a known class 2 fax command, I added this to change the
automatic "best capabilities" connection in the eicon HL-driver)
Armin
mac@melware.de
此差异已折叠。
The FAQ for isdn4linux
======================
Please note that there is a big FAQ available in the isdn4k-utils.
You find it in:
isdn4k-utils/FAQ/i4lfaq.sgml
In case you just want to see the FAQ online, or download the newest version,
you can have a look at my website:
https://www.mhessler.de/i4lfaq/ (view + download)
or:
https://www.isdn4linux.de/faq/4lfaq.html (view)
As the extension tells, the FAQ is in SGML format, and you can convert it
into text/html/... format by using the sgml2txt/sgml2html/... tools.
Alternatively, you can also do a 'configure; make all' in the FAQ directory.
Please have a look at the FAQ before posting anything in the Mailinglist,
or the newsgroup!
Matthias Hessler
hessler@isdn4linux.de
$Id: README.audio,v 1.8 1999/07/11 17:17:29 armin Exp $
ISDN subsystem for Linux.
Description of audio mode.
When enabled during kernel configuration, the tty emulator of the ISDN
subsystem is capable of a reduced set of commands to support audio.
This document describes the commands supported and the format of
audio data.
Commands for enabling/disabling audio mode:
AT+FCLASS=8 Enable audio mode.
This affects the following registers:
S18: Bits 0 and 2 are set.
S16: Set to 48 and any further change to
larger values is blocked.
AT+FCLASS=0 Disable audio mode.
Register 18 is set to 4.
AT+FCLASS=? Show possible modes.
AT+FCLASS? Report current mode (0 or 8).
Commands supported in audio mode:
All audio mode commands have one of the following forms:
AT+Vxx? Show current setting.
AT+Vxx=? Show possible settings.
AT+Vxx=v Set simple parameter.
AT+Vxx=v,v ... Set complex parameter.
where xx is a two-character code and v are alphanumerical parameters.
The following commands are supported:
AT+VNH=x Auto hangup setting. NO EFFECT, supported
for compatibility only.
AT+VNH? Always reporting "1"
AT+VNH=? Always reporting "1"
AT+VIP Reset all audio parameters.
AT+VLS=x Line select. x is one of the following:
0 = No device.
2 = Phone line.
AT+VLS=? Always reporting "0,2"
AT+VLS? Show current line.
AT+VRX Start recording. Emulator responds with
CONNECT and starts sending audio data to
the application. See below for data format
AT+VSD=x,y Set silence-detection parameters.
Possible parameters:
x = 0 ... 31 sensitivity threshold level.
(default 0 , deactivated)
y = 0 ... 255 range of interval in units
of 0.1 second. (default 70)
AT+VSD=? Report possible parameters.
AT+VSD? Show current parameters.
AT+VDD=x,y Set DTMF-detection parameters.
Only possible if online and during this connection.
Possible parameters:
x = 0 ... 15 sensitivity threshold level.
(default 0 , I4L soft-decode)
(1-15 soft-decode off, hardware on)
y = 0 ... 255 tone duration in units of 5ms.
Not for I4L soft decode (default 8, 40ms)
AT+VDD=? Report possible parameters.
AT+VDD? Show current parameters.
AT+VSM=x Select audio data format.
Possible parameters:
2 = ADPCM-2
3 = ADPCM-3
4 = ADPCM-4
5 = aLAW
6 = uLAW
AT+VSM=? Show possible audio formats.
AT+VTX Start audio playback. Emulator responds
with CONNECT and starts sending audio data
received from the application via phone line.
General behavior and description of data formats/protocol.
when a connection is made:
On incoming calls, if the application responds to a RING
with ATA, depending on the calling service, the emulator
responds with either CONNECT (data call) or VCON (voice call).
On outgoing voice calls, the emulator responds with VCON
upon connection setup.
Audio recording.
When receiving audio data, a kind of bisync protocol is used.
Upon AT+VRX command, the emulator responds with CONNECT, and
starts sending audio data to the application. There are several
escape sequences defined, all using DLE (0x10) as Escape char:
<DLE><ETX> End of audio data. (i.e. caused by a
hangup of the remote side) Emulator stops
recording, responding with VCON.
<DLE><DC4> Abort recording, (send by appl.) Emulator
stops recording, sends DLE,ETX.
<DLE><DLE> Escape sequence for DLE in data stream.
<DLE>0 Touchtone "0" received.
...
<DLE>9 Touchtone "9" received.
<DLE># Touchtone "#" received.
<DLE>* Touchtone "*" received.
<DLE>A Touchtone "A" received.
<DLE>B Touchtone "B" received.
<DLE>C Touchtone "C" received.
<DLE>D Touchtone "D" received.
<DLE>q quiet. Silence detected after non-silence.
<DLE>s silence. Silence detected from the
start of recording.
Currently unsupported DLE sequences:
<DLE>c FAX calling tone received.
<DLE>b busy tone received.
Audio playback.
When sending audio data, upon AT+VTX command, emulator responds with
CONNECT, and starts transferring data from application to the phone line.
The same DLE sequences apply to this mode.
Full-Duplex-Audio:
When _both_ commands for recording and playback are given in _one_
AT-command-line (i.e.: "AT+VTX+VRX"), full-duplex-mode is selected.
In this mode, the only way to stop recording is sending <DLE><DC4>
and the only way to stop playback is to send <DLE><ETX>.
Description of the "concap" encapsulation protocol interface
============================================================
The "concap" interface is intended to be used by network device
drivers that need to process an encapsulation protocol.
It is assumed that the protocol interacts with a linux network device by
- data transmission
- connection control (establish, release)
Thus, the mnemonic: "CONnection CONtrolling eNCAPsulation Protocol".
This is currently only used inside the isdn subsystem. But it might
also be useful to other kinds of network devices. Thus, if you want
to suggest changes that improve usability or performance of the
interface, please let me know. I'm willing to include them in future
releases (even if I needed to adapt the current isdn code to the
changed interface).
Why is this useful?
===================
The encapsulation protocol used on top of WAN connections or permanent
point-to-point links are frequently chosen upon bilateral agreement.
Thus, a device driver for a certain type of hardware must support
several different encapsulation protocols at once.
The isdn device driver did already support several different
encapsulation protocols. The encapsulation protocol is configured by a
user space utility (isdnctrl). The isdn network interface code then
uses several case statements which select appropriate actions
depending on the currently configured encapsulation protocol.
In contrast, LAN network interfaces always used a single encapsulation
protocol which is unique to the hardware type of the interface. The LAN
encapsulation is usually done by just sticking a header on the data. Thus,
traditional linux network device drivers used to process the
encapsulation protocol directly (usually by just providing a hard_header()
method in the device structure) using some hardware type specific support
functions. This is simple, direct and efficient. But it doesn't fit all
the requirements for complex WAN encapsulations.
The configurability of the encapsulation protocol to be used
makes isdn network interfaces more flexible, but also much more
complex than traditional lan network interfaces.
Many Encapsulation protocols used on top of WAN connections will not just
stick a header on the data. They also might need to set up or release
the WAN connection. They also might want to send other data for their
private purpose over the wire, e.g. ppp does a lot of link level
negotiation before the first piece of user data can be transmitted.
Such encapsulation protocols for WAN devices are typically more complex
than encapsulation protocols for lan devices. Thus, network interface
code for typical WAN devices also tends to be more complex.
In order to support Linux' x25 PLP implementation on top of
isdn network interfaces I could have introduced yet another branch to
the various case statements inside drivers/isdn/isdn_net.c.
This eventually made isdn_net.c even more complex. In addition, it made
isdn_net.c harder to maintain. Thus, by identifying an abstract
interface between the network interface code and the encapsulation
protocol, complexity could be reduced and maintainability could be
increased.
Likewise, a similar encapsulation protocol will frequently be needed by
several different interfaces of even different hardware type, e.g. the
synchronous ppp implementation used by the isdn driver and the
asynchronous ppp implementation used by the ppp driver have a lot of
similar code in them. By cleanly separating the encapsulation protocol
from the hardware specific interface stuff such code could be shared
better in future.
When operating over dial-up-connections (e.g. telephone lines via modem,
non-permanent virtual circuits of wide area networks, ISDN) many
encapsulation protocols will need to control the connection. Therefore,
some basic connection control primitives are supported. The type and
semantics of the connection (i.e the ISO layer where connection service
is provided) is outside our scope and might be different depending on
the encapsulation protocol used, e.g. for a ppp module using our service
on top of a modem connection a connect_request will result in dialing
a (somewhere else configured) remote phone number. For an X25-interface
module (LAPB semantics, as defined in Documentation/networking/x25-iface.txt)
a connect_request will ask for establishing a reliable lapb
datalink connection.
The encapsulation protocol currently provides the following
service primitives to the network device.
- create a new encapsulation protocol instance
- delete encapsulation protocol instance and free all its resources
- initialize (open) the encapsulation protocol instance for use.
- deactivate (close) an encapsulation protocol instance.
- process (xmit) data handed down by upper protocol layer
- receive data from lower (hardware) layer
- process connect indication from lower (hardware) layer
- process disconnect indication from lower (hardware) layer
The network interface driver accesses those primitives via callbacks
provided by the encapsulation protocol instance within a
struct concap_proto_ops.
struct concap_proto_ops{
/* create a new encapsulation protocol instance of same type */
struct concap_proto * (*proto_new) (void);
/* delete encapsulation protocol instance and free all its resources.
cprot may no longer be referenced after calling this */
void (*proto_del)(struct concap_proto *cprot);
/* initialize the protocol's data. To be called at interface startup
or when the device driver resets the interface. All services of the
encapsulation protocol may be used after this*/
int (*restart)(struct concap_proto *cprot,
struct net_device *ndev,
struct concap_device_ops *dops);
/* deactivate an encapsulation protocol instance. The encapsulation
protocol may not call any *dops methods after this. */
int (*close)(struct concap_proto *cprot);
/* process a frame handed down to us by upper layer */
int (*encap_and_xmit)(struct concap_proto *cprot, struct sk_buff *skb);
/* to be called for each data entity received from lower layer*/
int (*data_ind)(struct concap_proto *cprot, struct sk_buff *skb);
/* to be called when a connection was set up/down.
Protocols that don't process these primitives might fill in
dummy methods here */
int (*connect_ind)(struct concap_proto *cprot);
int (*disconn_ind)(struct concap_proto *cprot);
};
The data structures are defined in the header file include/linux/concap.h.
A Network interface using encapsulation protocols must also provide
some service primitives to the encapsulation protocol:
- request data being submitted by lower layer (device hardware)
- request a connection being set up by lower layer
- request a connection being released by lower layer
The encapsulation protocol accesses those primitives via callbacks
provided by the network interface within a struct concap_device_ops.
struct concap_device_ops{
/* to request data be submitted by device */
int (*data_req)(struct concap_proto *, struct sk_buff *);
/* Control methods must be set to NULL by devices which do not
support connection control. */
/* to request a connection be set up */
int (*connect_req)(struct concap_proto *);
/* to request a connection be released */
int (*disconn_req)(struct concap_proto *);
};
The network interface does not explicitly provide a receive service
because the encapsulation protocol directly calls netif_rx().
An encapsulation protocol itself is actually the
struct concap_proto{
struct net_device *net_dev; /* net device using our service */
struct concap_device_ops *dops; /* callbacks provided by device */
struct concap_proto_ops *pops; /* callbacks provided by us */
int flags;
void *proto_data; /* protocol specific private data, to
be accessed via *pops methods only*/
/*
:
whatever
:
*/
};
Most of this is filled in when the device requests the protocol to
be reset (opend). The network interface must provide the net_dev and
dops pointers. Other concap_proto members should be considered private
data that are only accessed by the pops callback functions. Likewise,
a concap proto should access the network device's private data
only by means of the callbacks referred to by the dops pointer.
A possible extended device structure which uses the connection controlling
encapsulation services could look like this:
struct concap_device{
struct net_device net_dev;
struct my_priv /* device->local stuff */
/* the my_priv struct might contain a
struct concap_device_ops *dops;
to provide the device specific callbacks
*/
struct concap_proto *cprot; /* callbacks provided by protocol */
};
Misc Thoughts
=============
The concept of the concap proto might help to reuse protocol code and
reduce the complexity of certain network interface implementations.
The trade off is that it introduces yet another procedure call layer
when processing the protocol. This has of course some impact on
performance. However, typically the concap interface will be used by
devices attached to slow lines (like telephone, isdn, leased synchronous
lines). For such slow lines, the overhead is probably negligible.
This might no longer hold for certain high speed WAN links (like
ATM).
If general linux network interfaces explicitly supported concap
protocols (e.g. by a member struct concap_proto* in struct net_device)
then the interface of the service function could be changed
by passing a pointer of type (struct net_device*) instead of
type (struct concap_proto*). Doing so would make many of the service
functions compatible to network device support functions.
e.g. instead of the concap protocol's service function
int (*encap_and_xmit)(struct concap_proto *cprot, struct sk_buff *skb);
we could have
int (*encap_and_xmit)(struct net_device *ndev, struct sk_buff *skb);
As this is compatible to the dev->hard_start_xmit() method, the device
driver could directly register the concap protocol's encap_and_xmit()
function as its hard_start_xmit() method. This would eliminate one
procedure call layer.
The device's data request function could also be defined as
int (*data_req)(struct net_device *ndev, struct sk_buff *skb);
This might even allow for some protocol stacking. And the network
interface might even register the same data_req() function directly
as its hard_start_xmit() method when a zero layer encapsulation
protocol is configured. Thus, eliminating the performance penalty
of the concap interface when a trivial concap protocol is used.
Nevertheless, the device remains able to support encapsulation
protocol configuration.
The isdn diversion services are a supporting module working together with
the isdn4linux and the HiSax module for passive cards.
Active cards, TAs and cards using a own or other driver than the HiSax
module need to be adapted to the HL<->LL interface described in a separate
document. The diversion services may be used with all cards supported by
the HiSax driver.
The diversion kernel interface and controlling tool divertctrl were written
by Werner Cornelius (werner@isdn4linux.de or werner@titro.de) under the
GNU General Public License.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
Table of contents
=================
1. Features of the i4l diversion services
(Or what can the i4l diversion services do for me)
2. Required hard- and software
3. Compiling, installing and loading/unloading the module
Tracing calling and diversion information
4. Tracing calling and diversion information
5. Format of the divert device ASCII output
1. Features of the i4l diversion services
(Or what can the i4l diversion services do for me)
The i4l diversion services offers call forwarding and logging normally
only supported by isdn phones. Incoming calls may be diverted
unconditionally (CFU), when not reachable (CFNR) or on busy condition
(CFB).
The diversions may be invoked statically in the providers exchange
as normally done by isdn phones. In this case all incoming calls
with a special (or all) service identifiers are forwarded if the
forwarding reason is met. Activated static services may also be
interrogated (queried).
The i4l diversion services additionally offers a dynamic version of
call forwarding which is not preprogrammed inside the providers exchange
but dynamically activated by i4l.
In this case all incoming calls are checked by rules that may be
compared to the mechanism of ipfwadm or ipchains. If a given rule matches
the checking process is finished and the rule matching will be applied
to the call.
The rules include primary and secondary service identifiers, called
number and subaddress, callers number and subaddress and whether the rule
matches to all filtered calls or only those when all B-channel resources
are exhausted.
Actions that may be invoked by a rule are ignore, proceed, reject,
direct divert or delayed divert of a call.
All incoming calls matching a rule except the ignore rule a reported and
logged as ASCII via the proc filesystem (/proc/net/isdn/divert). If proceed
is selected the call will be held in a proceeding state (without ringing)
for a certain amount of time to let an external program or client decide
how to handle the call.
2. Required hard- and software
For using the i4l diversion services the isdn line must be of a EURO/DSS1
type. Additionally the i4l services only work together with the HiSax
driver for passive isdn cards. All HiSax supported cards may be used for
the diversion purposes.
The static diversion services require the provider having static services
CFU, CFNR, CFB activated on an MSN-line. The static services may not be
used on a point-to-point connection. Further the static services are only
available in some countries (for example germany). Countries requiring the
keypad protocol for activating static diversions (like the netherlands) are
not supported but may use the tty devices for this purpose.
The dynamic diversion services may be used in all countries if the provider
enables the feature CF (call forwarding). This should work on both MSN- and
point-to-point lines.
To add and delete rules the additional divertctrl program is needed. This
program is part of the isdn4kutils package.
3. Compiling, installing and loading/unloading the module
Tracing calling and diversion information
To compile the i4l code with diversion support you need to say yes to the
DSS1 diversion services when selecting the i4l options in the kernel
config (menuconfig or config).
After having properly activated a make modules and make modules_install all
required modules will be correctly installed in the needed modules dirs.
As the diversion services are currently not included in the scripts of most
standard distributions you will have to add a "insmod dss1_divert" after
having loaded the global isdn module.
The module can be loaded without any command line parameters.
If the module is actually loaded and active may be checked with a
"cat /proc/modules" or "ls /proc/net/isdn/divert". The divert file is
dynamically created by the diversion module and removed when the module is
unloaded.
4. Tracing calling and diversion information
You also may put a "cat /proc/net/isdn/divert" in the background with the
output redirected to a file. Then all actions of the module are logged.
The divert file in the proc system may be opened more than once, so in
conjunction with inetd and a small remote client on other machines inside
your network incoming calls and reactions by the module may be shown on
every listening machine.
If a call is reported as proceeding an external program or client may
specify during a certain amount of time (normally 4 to 10 seconds) what
to do with that call.
To unload the module all open files to the device in the proc system must
be closed. Otherwise the module (and isdn.o) may not be unloaded.
5. Format of the divert device ASCII output
To be done later
Fax with isdn4linux
===================
When enabled during kernel configuration, the tty emulator
of the ISDN subsystem is capable of the Fax Class 2 commands.
This only makes sense under the following conditions :
- You need the commands as dummy, because you are using
hylafax (with patch) for AVM capi.
- You want to use the fax capabilities of your isdn-card.
(supported cards are listed below)
NOTE: This implementation does *not* support fax with passive
ISDN-cards (known as softfax). The low-level driver of
the ISDN-card and/or the card itself must support this.
Supported ISDN-Cards
--------------------
Eicon DIVA Server BRI/PCI
- full support with both B-channels.
Eicon DIVA Server 4BRI/PCI
- full support with all B-channels.
Eicon DIVA Server PRI/PCI
- full support on amount of B-channels
depending on DSPs on board.
The command set is known as Class 2 (not Class 2.0) and
can be activated by AT+FCLASS=2
The interface between the link-level-module and the hardware-level driver
is described in the files INTERFACE.fax and INTERFACE.
Armin
mac@melware.de
The driver for the HFC-PCI and HFC-PCI-A chips from CCD may be used
for many OEM cards using this chips.
Additionally the driver has a special feature which makes it possible
to read the echo-channel of the isdn bus. So all frames in both directions
may be logged.
When the echo logging feature is used the number of available B-channels
for a HFC-PCI card is reduced to 1. Of course this is only relevant to
the card, not to the isdn line.
To activate the echo mode the following ioctls must be entered:
hisaxctrl <driver/cardname> 10 1
This reduces the available channels to 1. There must not be open connections
through this card when entering the command.
And then:
hisaxctrl <driver/cardname> 12 1
This enables the echo mode. If Hex logging is activated the isdnctrlx
devices show a output with a line beginning of HEX: for the providers
exchange and ECHO: for isdn devices sending to the provider.
If more than one HFC-PCI cards are installed, a specific card may be selected
at the hisax module load command line. Supply the load command with the desired
IO-address of the desired card.
Example:
There tree cards installed in your machine at IO-base addresses 0xd000, 0xd400
and 0xdc00
If you want to use the card at 0xd400 standalone you should supply the insmod
or depmod with type=35 io=0xd400.
If you want to use all three cards, but the order needs to be at 0xdc00,0xd400,
0xd000 you may give the parameters type=35,35,35 io=0xdc00,0xd400,0xd00
Then the desired card will be the initialised in the desired order.
If the io parameter is used the io addresses of all used cards should be
supplied else the parameter is assumed 0 and a auto search for a free card is
invoked which may not give the wanted result.
Comments and reports to werner@isdn4linux.de or werner@isdn-development.de
Some additional information for setting up a syncPPP
connection using network interfaces.
---------------------------------------------------------------
You need one thing beside the isdn4linux package:
a patched pppd .. (I called it ipppd to show the difference)
Compiling isdn4linux with sync PPP:
-----------------------------------
To compile isdn4linux with the sync PPP part, you have
to answer the appropriate question when doing a "make config"
Don't forget to load the slhc.o
module before the isdn.o module, if VJ-compression support
is not compiled into your kernel. (e.g if you have no PPP or
CSLIP in the kernel)
Using isdn4linux with sync PPP:
-------------------------------
Sync PPP is just another encapsulation for isdn4linux. The
name to enable sync PPP encapsulation is 'syncppp' .. e.g:
/sbin/isdnctrl encap ippp0 syncppp
The name of the interface is here 'ippp0'. You need
one interface with the name 'ippp0' to saturate the
ipppd, which checks the ppp version via this interface.
Currently, all devices must have the name ipppX where
'X' is a decimal value.
To set up a PPP connection you need the ipppd .. You must start
the ipppd once after installing the modules. The ipppd
communicates with the isdn4linux link-level driver using the
/dev/ippp0 to /dev/ippp15 devices. One ipppd can handle
all devices at once. If you want to use two PPP connections
at the same time, you have to connect the ipppd to two
devices .. and so on.
I've implemented one additional option for the ipppd:
'useifip' will get (if set to not 0.0.0.0) the IP address
for the negotiation from the attached network-interface.
(also: ipppd will try to negotiate pointopoint IP as remote IP)
You must disable BSD-compression, this implementation can't
handle compressed packets.
Check the etc/rc.isdn.syncppp in the isdn4kernel-util package
for an example setup script.
To use the MPPP stuff, you must configure a slave device
with isdn4linux. Now call the ipppd with the '+mp' option.
To increase the number of links, you must use the
'addlink' option of the isdnctrl tool. (rc.isdn.syncppp.MPPP is
an example script)
enjoy it,
michael
X.25 support within isdn4linux
==============================
This is alpha/beta test code. Use it completely at your own risk.
As new versions appear, the stuff described here might suddenly change
or become invalid without notice.
Keep in mind:
You are using several new parts of the 2.2.x kernel series which
have not been tested in a large scale. Therefore, you might encounter
more bugs as usual.
- If you connect to an X.25 neighbour not operated by yourself, ASK the
other side first. Be prepared that bugs in the protocol implementation
might result in problems.
- This implementation has never wiped out my whole hard disk yet. But as
this is experimental code, don't blame me if that happened to you.
Backing up important data will never harm.
- Monitor your isdn connections while using this software. This should
prevent you from undesired phone bills in case of driver problems.
How to configure the kernel
===========================
The ITU-T (former CCITT) X.25 network protocol layer has been implemented
in the Linux source tree since version 2.1.16. The isdn subsystem might be
useful to run X.25 on top of ISDN. If you want to try it, select
"CCITT X.25 Packet Layer"
from the networking options as well as
"ISDN Support" and "X.25 PLP on Top of ISDN"
from the ISDN subsystem options when you configure your kernel for
compilation. You currently also need to enable
"Prompt for development and/or incomplete code/drivers" from the
"Code maturity level options" menu. For the x25trace utility to work
you also need to enable "Packet socket".
For local testing it is also recommended to enable the isdnloop driver
from the isdn subsystem's configuration menu.
For testing, it is recommended that all isdn drivers and the X.25 PLP
protocol are compiled as loadable modules. Like this, you can recover
from certain errors by simply unloading and reloading the modules.
What's it for? How to use it?
=============================
X.25 on top of isdn might be useful with two different scenarios:
- You might want to access a public X.25 data network from your Linux box.
You can use i4l if you were physically connected to the X.25 switch
by an ISDN B-channel (leased line as well as dial up connection should
work).
This corresponds to ITU-T recommendation X.31 Case A (circuit-mode
access to PSPDN [packet switched public data network]).
NOTE: X.31 also covers a Case B (access to PSPDN via virtual
circuit / packet mode service). The latter mode (which in theory
also allows using the D-channel) is not supported by isdn4linux.
It should however be possible to establish such packet mode connections
with certain active isdn cards provided that the firmware supports X.31
and the driver exports this functionality to the user. Currently,
the AVM B1 driver is the only driver which does so. (It should be
possible to access D-channel X.31 with active AVM cards using the
CAPI interface of the AVM-B1 driver).
- Or you might want to operate certain ISDN teleservices on your linux
box. A lot of those teleservices run on top of the ISO-8208
(DTE-DTE mode) network layer protocol. ISO-8208 is essentially the
same as ITU-T X.25.
Popular candidates of such teleservices are EUROfile transfer or any
teleservice applying ITU-T recommendation T.90.
To use the X.25 protocol on top of isdn, just create an isdn network
interface as usual, configure your own and/or peer's ISDN numbers,
and choose x25iface encapsulation by
isdnctrl encap <iface-name> x25iface.
Once encap is set like this, the device can be used by the X.25 packet layer.
All the stuff needed for X.25 is implemented inside the isdn link
level (mainly isdn_net.c and some new source files). Thus, it should
work with every existing HL driver. I was able to successfully open X.25
connections on top of the isdnloop driver and the hisax driver.
"x25iface"-encapsulation bypasses demand dialing. Dialing will be
initiated when the upper (X.25 packet) layer requests the lapb datalink to
be established. But hangup timeout is still active. Whenever a hangup
occurs, all existing X.25 connections on that link will be cleared
It is recommended to use sufficiently large hangup-timeouts for the
isdn interfaces.
In order to set up a conforming protocol stack you also need to
specify the proper l2_prot parameter:
To operate in ISO-8208 X.25 DTE-DTE mode, use
isdnctrl l2_prot <iface-name> x75i
To access an X.25 network switch via isdn (your linux box is the DTE), use
isdnctrl l2_prot <iface-name> x25dte
To mimic an X.25 network switch (DCE side of the connection), use
isdnctrl l2_prot <iface-name> x25dce
However, x25dte or x25dce is currently not supported by any real HL
level driver. The main difference between x75i and x25dte/dce is that
x25d[tc]e uses fixed lap_b addresses. With x75i, the side which
initiates the isdn connection uses the DTE's lap_b address while the
called side used the DCE's lap_b address. Thus, l2_prot x75i might
probably work if you access a public X.25 network as long as the
corresponding isdn connection is set up by you. At least one test
was successful to connect via isdn4linux to an X.25 switch using this
trick. At the switch side, a terminal adapter X.21 was used to connect
it to the isdn.
How to set up a test installation?
==================================
To test X.25 on top of isdn, you need to get
- a recent version of the "isdnctrl" program that supports setting the new
X.25 specific parameters.
- the x25-utils-2.X package from
ftp://ftp.hes.iki.fi/pub/ham/linux/ax25/x25utils-*
(don't confuse the x25-utils with the ax25-utils)
- an application program that uses linux PF_X25 sockets (some are
contained in the x25-util package).
Before compiling the user level utilities make sure that the compiler/
preprocessor will fetch the proper kernel header files of this kernel
source tree. Either make /usr/include/linux a symbolic link pointing to
this kernel's include/linux directory or set the appropriate compiler flags.
When all drivers and interfaces are loaded and configured you need to
ifconfig the network interfaces up and add X.25-routes to them. Use
the usual ifconfig tool.
ifconfig <iface-name> up
But a special x25route tool (distributed with the x25-util package)
is needed to set up X.25 routes. I.e.
x25route add 01 <iface-name>
will cause all x.25 connections to the destination X.25-address
"01" to be routed to your created isdn network interface.
There are currently no real X.25 applications available. However, for
tests, the x25-utils package contains a modified version of telnet
and telnetd that uses X.25 sockets instead of tcp/ip sockets. You can
use those for your first tests. Furthermore, you might check
ftp://ftp.hamburg.pop.de/pub/LOCAL/linux/i4l-eft/ which contains some
alpha-test implementation ("eftp4linux") of the EUROfile transfer
protocol.
The scripts distributed with the eftp4linux test releases might also
provide useful examples for setting up X.25 on top of isdn.
The x25-utility package also contains an x25trace tool that can be
used to monitor X.25 packets received by the network interfaces.
The /proc/net/x25* files also contain useful information.
- Henner
simple isdn4linux PPP FAQ .. to be continued .. not 'debugged'
-------------------------------------------------------------------
Q01: what's pppd, ipppd, syncPPP, asyncPPP ??
Q02: error message "this system lacks PPP support"
Q03: strange information using 'ifconfig'
Q04: MPPP?? What's that and how can I use it ...
Q05: I tried MPPP but it doesn't work
Q06: can I use asynchronous PPP encapsulation with network devices
Q07: A SunISDN machine can't connect to my i4l system
Q08: I wanna talk to several machines, which need different configs
Q09: Starting the ipppd, I get only error messages from i4l
Q10: I wanna use dynamic IP address assignment
Q11: I can't connect. How can I check where the problem is.
Q12: How can I reduce login delay?
-------------------------------------------------------------------
Q01: pppd, ipppd, syncPPP, asyncPPP .. what is that ?
what should I use?
A: The pppd is for asynchronous PPP .. asynchronous means
here, the framing is character based. (e.g when
using ttyI* or tty* devices)
The ipppd handles PPP packets coming in HDLC
frames (bit based protocol) ... The PPP driver
in isdn4linux pushes all IP packets direct
to the network layer and all PPP protocol
frames to the /dev/ippp* device.
So, the ipppd is a simple external network
protocol handler.
If you login into a remote machine using the
/dev/ttyI* devices and then enable PPP on the
remote terminal server -> use the 'old' pppd
If your remote side immediately starts to send
frames ... you probably connect to a
syncPPP machine .. use the network device part
of isdn4linux with the 'syncppp' encapsulation
and make sure, that the ipppd is running and
connected to at least one /dev/ippp*. Check the
isdn4linux manual on how to configure a network device.
--
Q02: when I start the ipppd .. I only get the
error message "this system lacks PPP support"
A: check that at least the device 'ippp0' exists.
(you can check this e.g with the program 'ifconfig')
The ipppd NEEDS this device under THIS name ..
If this device doesn't exists, use:
isdnctrl addif ippp0
isdnctrl encap ippp0 syncppp
... (see isdn4linux doc for more) ...
A: Maybe you have compiled the ipppd with another
kernel source tree than the kernel you currently
run ...
--
Q03: when I list the netdevices with ifconfig I see, that
my ISDN interface has a HWaddr and IRQ=0 and Base
address = 0
A: The device is a fake ethernet device .. ignore IRQ and baseaddr
You need the HWaddr only for ethernet encapsulation.
--
Q04: MPPP?? What's that and how can I use it ...
A: MPPP or MP or MPP (Warning: MP is also an
acronym for 'Multi Processor') stands for
Multi Point to Point and means bundling
of several channels to one logical stream.
To enable MPPP negotiation you must call the
ipppd with the '+mp' option.
You must also configure a slave device for
every additional channel. (see the i4l manual
for more)
To use channel bundling you must first activate
the 'master' or initial call. Now you can add
the slave channels with the command:
isdnctrl addlink <device>
e.g:
isdnctrl addlink ippp0
This is different from other encapsulations of
isdn4linux! With syncPPP, there is no automatic
activation of slave devices.
--
Q05: I tried MPPP but it doesn't work .. the ipppd
writes in the debug log something like:
.. rcvd [0][proto=0x3d] c0 00 00 00 80 fd 01 01 00 0a ...
.. sent [0][LCP ProtRej id=0x2 00 3d c0 00 00 00 80 fd 01 ...
A: you forgot to compile MPPP/RFC1717 support into the
ISDN Subsystem. Recompile with this option enabled.
--
Q06: can I use asynchronous PPP encapsulation
over the network interface of isdn4linux ..
A: No .. that's not possible .. Use the standard
PPP package over the /dev/ttyI* devices. You
must not use the ipppd for this.
--
Q07: A SunISDN machine tries to connect my i4l system,
which doesn't work.
Checking the debug log I just saw garbage like:
!![ ... fill in the line ... ]!!
A: The Sun tries to talk asynchronous PPP ... i4l
can't understand this ... try to use the ttyI*
devices with the standard PPP/pppd package
A: (from Alexanter Strauss: )
!![ ... fill in mail ]!!
--
Q08: I wanna talk to remote machines, which need
a different configuration. The only way
I found to do this is to kill the ipppd and
start a new one with another config to connect
to the second machine.
A: you must bind a network interface explicitly to
an ippp device, where you can connect a (for this
interface) individually configured ipppd.
--
Q09: When I start the ipppd I only get error messages
from the i4l driver ..
A: When starting, the ipppd calls functions which may
trigger a network packet. (e.g gethostbyname()).
Without the ipppd (at this moment, it is not
fully started) we can't handle this network request.
Try to configure hostnames necessary for the ipppd
in your local /etc/hosts file or in a way, that
your system can resolve it without using an
isdn/ippp network-interface.
--
Q10: I wanna use dynamic IP address assignment ... How
must I configure the network device.
A: At least you must have a route which forwards
a packet to the ippp network-interface to trigger
the dial-on-demand.
A default route to the ippp-interface will work.
Now you must choose a dummy IP address for your
interface.
If for some reason you can't set the default
route to the ippp interface, you may take any
address of the subnet from which you expect your
dynamic IP number and set a 'network route' for
this subnet to the ippp interface.
To allow overriding of the dummy address you
must call the ipppd with the 'ipcp-accept-local' option.
A: You must know, how the ipppd gets the addresses it wanna
configure. If you don't give any option, the ipppd
tries to negotiate the local host address!
With the option 'noipdefault' it requests an address
from the remote machine. With 'useifip' it gets the
addresses from the net interface. Or you set the address
on the option line with the <a.b.c.d:e.f.g.h> option.
Note: the IP address of the remote machine must be configured
locally or the remote machine must send it in an IPCP request.
If your side doesn't know the IP address after negotiation, it
closes the connection!
You must allow overriding of address with the 'ipcp-accept-*'
options, if you have set your own or the remote address
explicitly.
A: Maybe you try these options .. e.g:
/sbin/ipppd :$REMOTE noipdefault /dev/ippp0
where REMOTE must be the address of the remote machine (the
machine, which gives you your address)
--
Q11: I can't connect. How can I check where the problem is.
A: A good help log is the debug output from the ipppd...
Check whether you can find there:
- only a few LCP-conf-req SENT messages (less then 10)
and then a Term-REQ:
-> check whether your ISDN card is well configured
it seems, that your machine doesn't dial
(IRQ,IO,Proto, etc problems)
Configure your ISDN card to print debug messages and
check the /dev/isdnctrl output next time. There
you can see, whether there is activity on the card/line.
- there are at least a few RECV messages in the log:
-> fine: your card is dialing and your remote machine
tries to talk with you. Maybe only a missing
authentication. Check your ipppd configuration again.
- the ipppd exits for some reason:
-> not good ... check /var/adm/syslog and /var/adm/daemon.
Could be a bug in the ipppd.
--
Q12: How can I reduce login delay?
A: Log a login session ('debug' log) and check which options
your remote side rejects. Next time configure your ipppd
to not negotiate these options. Another 'side effect' is, that
this increases redundancy. (e.g your remote side is buggy and
rejects options in a wrong way).
...@@ -23,8 +23,8 @@ running, the suggested command should tell you. ...@@ -23,8 +23,8 @@ running, the suggested command should tell you.
Again, keep in mind that this list assumes you are already functionally Again, keep in mind that this list assumes you are already functionally
running a Linux kernel. Also, not all tools are necessary on all running a Linux kernel. Also, not all tools are necessary on all
systems; obviously, if you don't have any ISDN hardware, for example, systems; obviously, if you don't have any PC Card hardware, for example,
you probably needn't concern yourself with isdn4k-utils. you probably needn't concern yourself with pcmciautils.
====================== =============== ======================================== ====================== =============== ========================================
Program Minimal version Command to check the version Program Minimal version Command to check the version
...@@ -45,7 +45,6 @@ btrfs-progs 0.18 btrfsck ...@@ -45,7 +45,6 @@ btrfs-progs 0.18 btrfsck
pcmciautils 004 pccardctl -V pcmciautils 004 pccardctl -V
quota-tools 3.09 quota -V quota-tools 3.09 quota -V
PPP 2.4.0 pppd --version PPP 2.4.0 pppd --version
isdn4k-utils 3.1pre1 isdnctrl 2>&1|grep version
nfs-utils 1.0.5 showmount --version nfs-utils 1.0.5 showmount --version
procps 3.2.0 ps --version procps 3.2.0 ps --version
oprofile 0.9 oprofiled --version oprofile 0.9 oprofiled --version
...@@ -279,12 +278,6 @@ which can be made by:: ...@@ -279,12 +278,6 @@ which can be made by::
as root. as root.
Isdn4k-utils
------------
Due to changes in the length of the phone number field, isdn4k-utils
needs to be recompiled or (preferably) upgraded.
NFS-utils NFS-utils
--------- ---------
...@@ -448,11 +441,6 @@ PPP ...@@ -448,11 +441,6 @@ PPP
- <ftp://ftp.samba.org/pub/ppp/> - <ftp://ftp.samba.org/pub/ppp/>
Isdn4k-utils
------------
- <ftp://ftp.isdn4linux.de/pub/isdn4linux/utils/>
NFS-utils NFS-utils
--------- ---------
......
...@@ -8371,9 +8371,7 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/kkeil/isdn-2.6.git ...@@ -8371,9 +8371,7 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/kkeil/isdn-2.6.git
S: Maintained S: Maintained
F: Documentation/isdn/ F: Documentation/isdn/
F: drivers/isdn/ F: drivers/isdn/
F: include/linux/isdn.h
F: include/linux/isdn/ F: include/linux/isdn/
F: include/uapi/linux/isdn.h
F: include/uapi/linux/isdn/ F: include/uapi/linux/isdn/
IT87 HARDWARE MONITORING DRIVER IT87 HARDWARE MONITORING DRIVER
......
...@@ -21,27 +21,6 @@ menuconfig ISDN ...@@ -21,27 +21,6 @@ menuconfig ISDN
if ISDN if ISDN
menuconfig ISDN_I4L
tristate "Old ISDN4Linux (deprecated)"
depends on TTY
---help---
This driver allows you to use an ISDN adapter for networking
connections and as dialin/out device. The isdn-tty's have a built
in AT-compatible modem emulator. Network devices support autodial,
channel-bundling, callback and caller-authentication without having
a daemon running. A reduced T.70 protocol is supported with tty's
suitable for German BTX. On D-Channel, the protocols EDSS1
(Euro-ISDN) and 1TR6 (German style) are supported. See
<file:Documentation/isdn/README> for more information.
ISDN support in the linux kernel is moving towards a new API,
called CAPI (Common ISDN Application Programming Interface).
Therefore the old ISDN4Linux layer will eventually become obsolete.
It is still available, though, for use with adapters that are not
supported by the new CAPI subsystem yet.
source "drivers/isdn/i4l/Kconfig"
menuconfig ISDN_CAPI menuconfig ISDN_CAPI
tristate "CAPI 2.0 subsystem" tristate "CAPI 2.0 subsystem"
help help
...@@ -71,9 +50,4 @@ source "drivers/isdn/hysdn/Kconfig" ...@@ -71,9 +50,4 @@ source "drivers/isdn/hysdn/Kconfig"
source "drivers/isdn/mISDN/Kconfig" source "drivers/isdn/mISDN/Kconfig"
config ISDN_HDLC
tristate
select CRC_CCITT
select BITREVERSE
endif # ISDN endif # ISDN
...@@ -7,7 +7,5 @@ obj-$(CONFIG_ISDN_I4L) += i4l/ ...@@ -7,7 +7,5 @@ obj-$(CONFIG_ISDN_I4L) += i4l/
obj-$(CONFIG_ISDN_CAPI) += capi/ obj-$(CONFIG_ISDN_CAPI) += capi/
obj-$(CONFIG_MISDN) += mISDN/ obj-$(CONFIG_MISDN) += mISDN/
obj-$(CONFIG_ISDN) += hardware/ obj-$(CONFIG_ISDN) += hardware/
obj-$(CONFIG_ISDN_DIVERSION) += divert/
obj-$(CONFIG_ISDN_DRV_LOOP) += isdnloop/
obj-$(CONFIG_HYSDN) += hysdn/ obj-$(CONFIG_HYSDN) += hysdn/
obj-$(CONFIG_ISDN_DRV_GIGASET) += gigaset/ obj-$(CONFIG_ISDN_DRV_GIGASET) += gigaset/
...@@ -27,15 +27,6 @@ config ISDN_CAPI_MIDDLEWARE ...@@ -27,15 +27,6 @@ config ISDN_CAPI_MIDDLEWARE
device. If you want to use pppd with pppdcapiplugin to dial up to device. If you want to use pppd with pppdcapiplugin to dial up to
your ISP, say Y here. your ISP, say Y here.
config ISDN_CAPI_CAPIDRV
tristate "CAPI2.0 capidrv interface support"
depends on ISDN_I4L
help
This option provides the glue code to hook up CAPI driven cards to
the legacy isdn4linux link layer. If you have a card which is
supported by a CAPI driver, but still want to use old features like
ippp interfaces or ttyI emulation, say Y/M here.
config ISDN_CAPI_CAPIDRV_VERBOSE config ISDN_CAPI_CAPIDRV_VERBOSE
bool "Verbose reason code reporting" bool "Verbose reason code reporting"
depends on ISDN_CAPI_CAPIDRV depends on ISDN_CAPI_CAPIDRV
......
此差异已折叠。
/* $Id: capidrv.h,v 1.2.8.2 2001/09/23 22:24:33 kai Exp $
*
* ISDN4Linux Driver, using capi20 interface (kernelcapi)
*
* Copyright 1997 by Carsten Paeth <calle@calle.de>
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
#ifndef __CAPIDRV_H__
#define __CAPIDRV_H__
/*
* LISTEN state machine
*/
#define ST_LISTEN_NONE 0 /* L-0 */
#define ST_LISTEN_WAIT_CONF 1 /* L-0.1 */
#define ST_LISTEN_ACTIVE 2 /* L-1 */
#define ST_LISTEN_ACTIVE_WAIT_CONF 3 /* L-1.1 */
#define EV_LISTEN_REQ 1 /* L-0 -> L-0.1
L-1 -> L-1.1 */
#define EV_LISTEN_CONF_ERROR 2 /* L-0.1 -> L-0
L-1.1 -> L-1 */
#define EV_LISTEN_CONF_EMPTY 3 /* L-0.1 -> L-0
L-1.1 -> L-0 */
#define EV_LISTEN_CONF_OK 4 /* L-0.1 -> L-1
L-1.1 -> L.1 */
/*
* per plci state machine
*/
#define ST_PLCI_NONE 0 /* P-0 */
#define ST_PLCI_OUTGOING 1 /* P-0.1 */
#define ST_PLCI_ALLOCATED 2 /* P-1 */
#define ST_PLCI_ACTIVE 3 /* P-ACT */
#define ST_PLCI_INCOMING 4 /* P-2 */
#define ST_PLCI_FACILITY_IND 5 /* P-3 */
#define ST_PLCI_ACCEPTING 6 /* P-4 */
#define ST_PLCI_DISCONNECTING 7 /* P-5 */
#define ST_PLCI_DISCONNECTED 8 /* P-6 */
#define ST_PLCI_RESUMEING 9 /* P-0.Res */
#define ST_PLCI_RESUME 10 /* P-Res */
#define ST_PLCI_HELD 11 /* P-HELD */
#define EV_PLCI_CONNECT_REQ 1 /* P-0 -> P-0.1
*/
#define EV_PLCI_CONNECT_CONF_ERROR 2 /* P-0.1 -> P-0
*/
#define EV_PLCI_CONNECT_CONF_OK 3 /* P-0.1 -> P-1
*/
#define EV_PLCI_FACILITY_IND_UP 4 /* P-0 -> P-1
*/
#define EV_PLCI_CONNECT_IND 5 /* P-0 -> P-2
*/
#define EV_PLCI_CONNECT_ACTIVE_IND 6 /* P-1 -> P-ACT
*/
#define EV_PLCI_CONNECT_REJECT 7 /* P-2 -> P-5
P-3 -> P-5
*/
#define EV_PLCI_DISCONNECT_REQ 8 /* P-1 -> P-5
P-2 -> P-5
P-3 -> P-5
P-4 -> P-5
P-ACT -> P-5
P-Res -> P-5 (*)
P-HELD -> P-5 (*)
*/
#define EV_PLCI_DISCONNECT_IND 9 /* P-1 -> P-6
P-2 -> P-6
P-3 -> P-6
P-4 -> P-6
P-5 -> P-6
P-ACT -> P-6
P-Res -> P-6 (*)
P-HELD -> P-6 (*)
*/
#define EV_PLCI_FACILITY_IND_DOWN 10 /* P-0.1 -> P-5
P-1 -> P-5
P-ACT -> P-5
P-2 -> P-5
P-3 -> P-5
P-4 -> P-5
*/
#define EV_PLCI_DISCONNECT_RESP 11 /* P-6 -> P-0
*/
#define EV_PLCI_CONNECT_RESP 12 /* P-6 -> P-0
*/
#define EV_PLCI_RESUME_REQ 13 /* P-0 -> P-0.Res
*/
#define EV_PLCI_RESUME_CONF_OK 14 /* P-0.Res -> P-Res
*/
#define EV_PLCI_RESUME_CONF_ERROR 15 /* P-0.Res -> P-0
*/
#define EV_PLCI_RESUME_IND 16 /* P-Res -> P-ACT
*/
#define EV_PLCI_HOLD_IND 17 /* P-ACT -> P-HELD
*/
#define EV_PLCI_RETRIEVE_IND 18 /* P-HELD -> P-ACT
*/
#define EV_PLCI_SUSPEND_IND 19 /* P-ACT -> P-5
*/
#define EV_PLCI_CD_IND 20 /* P-2 -> P-5
*/
/*
* per ncci state machine
*/
#define ST_NCCI_PREVIOUS -1
#define ST_NCCI_NONE 0 /* N-0 */
#define ST_NCCI_OUTGOING 1 /* N-0.1 */
#define ST_NCCI_INCOMING 2 /* N-1 */
#define ST_NCCI_ALLOCATED 3 /* N-2 */
#define ST_NCCI_ACTIVE 4 /* N-ACT */
#define ST_NCCI_RESETING 5 /* N-3 */
#define ST_NCCI_DISCONNECTING 6 /* N-4 */
#define ST_NCCI_DISCONNECTED 7 /* N-5 */
#define EV_NCCI_CONNECT_B3_REQ 1 /* N-0 -> N-0.1 */
#define EV_NCCI_CONNECT_B3_IND 2 /* N-0 -> N.1 */
#define EV_NCCI_CONNECT_B3_CONF_OK 3 /* N-0.1 -> N.2 */
#define EV_NCCI_CONNECT_B3_CONF_ERROR 4 /* N-0.1 -> N.0 */
#define EV_NCCI_CONNECT_B3_REJECT 5 /* N-1 -> N-4 */
#define EV_NCCI_CONNECT_B3_RESP 6 /* N-1 -> N-2 */
#define EV_NCCI_CONNECT_B3_ACTIVE_IND 7 /* N-2 -> N-ACT */
#define EV_NCCI_RESET_B3_REQ 8 /* N-ACT -> N-3 */
#define EV_NCCI_RESET_B3_IND 9 /* N-3 -> N-ACT */
#define EV_NCCI_DISCONNECT_B3_IND 10 /* N-4 -> N.5 */
#define EV_NCCI_DISCONNECT_B3_CONF_ERROR 11 /* N-4 -> previous */
#define EV_NCCI_DISCONNECT_B3_REQ 12 /* N-1 -> N-4
N-2 -> N-4
N-3 -> N-4
N-ACT -> N-4 */
#define EV_NCCI_DISCONNECT_B3_RESP 13 /* N-5 -> N-0 */
#endif /* __CAPIDRV_H__ */
# SPDX-License-Identifier: GPL-2.0-only
# Makefile for the dss1_divert ISDN module
# Each configuration option enables a list of files.
obj-$(CONFIG_ISDN_DIVERSION) += dss1_divert.o
# Multipart objects.
dss1_divert-y := isdn_divert.o divert_procfs.o divert_init.o
/* $Id divert_init.c,v 1.5.6.2 2001/01/24 22:18:17 kai Exp $
*
* Module init for DSS1 diversion services for i4l.
*
* Copyright 1999 by Werner Cornelius (werner@isdn4linux.de)
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
#include <linux/module.h>
#include <linux/init.h>
#include <linux/kernel.h>
#include "isdn_divert.h"
MODULE_DESCRIPTION("ISDN4Linux: Call diversion support");
MODULE_AUTHOR("Werner Cornelius");
MODULE_LICENSE("GPL");
/****************************************/
/* structure containing interface to hl */
/****************************************/
isdn_divert_if divert_if = {
DIVERT_IF_MAGIC, /* magic value */
DIVERT_CMD_REG, /* register cmd */
ll_callback, /* callback routine from ll */
NULL, /* command still not specified */
NULL, /* drv_to_name */
NULL, /* name_to_drv */
};
/*************************/
/* Module interface code */
/* no cmd line parms */
/*************************/
static int __init divert_init(void)
{
int i;
if (divert_dev_init()) {
printk(KERN_WARNING "dss1_divert: cannot install device, not loaded\n");
return (-EIO);
}
if ((i = DIVERT_REG_NAME(&divert_if)) != DIVERT_NO_ERR) {
divert_dev_deinit();
printk(KERN_WARNING "dss1_divert: error %d registering module, not loaded\n", i);
return (-EIO);
}
printk(KERN_INFO "dss1_divert module successfully installed\n");
return (0);
}
/**********************/
/* Module deinit code */
/**********************/
static void __exit divert_exit(void)
{
unsigned long flags;
int i;
spin_lock_irqsave(&divert_lock, flags);
divert_if.cmd = DIVERT_CMD_REL; /* release */
if ((i = DIVERT_REG_NAME(&divert_if)) != DIVERT_NO_ERR) {
printk(KERN_WARNING "dss1_divert: error %d releasing module\n", i);
spin_unlock_irqrestore(&divert_lock, flags);
return;
}
if (divert_dev_deinit()) {
printk(KERN_WARNING "dss1_divert: device busy, remove cancelled\n");
spin_unlock_irqrestore(&divert_lock, flags);
return;
}
spin_unlock_irqrestore(&divert_lock, flags);
deleterule(-1); /* delete all rules and free mem */
deleteprocs();
printk(KERN_INFO "dss1_divert module successfully removed \n");
}
module_init(divert_init);
module_exit(divert_exit);
/* $Id: divert_procfs.c,v 1.11.6.2 2001/09/23 22:24:36 kai Exp $
*
* Filesystem handling for the diversion supplementary services.
*
* Copyright 1998 by Werner Cornelius (werner@isdn4linux.de)
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
#include <linux/module.h>
#include <linux/poll.h>
#include <linux/slab.h>
#ifdef CONFIG_PROC_FS
#include <linux/proc_fs.h>
#else
#include <linux/fs.h>
#endif
#include <linux/sched.h>
#include <linux/isdnif.h>
#include <net/net_namespace.h>
#include <linux/mutex.h>
#include "isdn_divert.h"
/*********************************/
/* Variables for interface queue */
/*********************************/
ulong if_used = 0; /* number of interface users */
static DEFINE_MUTEX(isdn_divert_mutex);
static struct divert_info *divert_info_head = NULL; /* head of queue */
static struct divert_info *divert_info_tail = NULL; /* pointer to last entry */
static DEFINE_SPINLOCK(divert_info_lock);/* lock for queue */
static wait_queue_head_t rd_queue;
/*********************************/
/* put an info buffer into queue */
/*********************************/
void
put_info_buffer(char *cp)
{
struct divert_info *ib;
unsigned long flags;
if (if_used <= 0)
return;
if (!cp)
return;
if (!*cp)
return;
if (!(ib = kmalloc(sizeof(struct divert_info) + strlen(cp), GFP_ATOMIC)))
return; /* no memory */
strcpy(ib->info_start, cp); /* set output string */
ib->next = NULL;
spin_lock_irqsave(&divert_info_lock, flags);
ib->usage_cnt = if_used;
if (!divert_info_head)
divert_info_head = ib; /* new head */
else
divert_info_tail->next = ib; /* follows existing messages */
divert_info_tail = ib; /* new tail */
/* delete old entrys */
while (divert_info_head->next) {
if ((divert_info_head->usage_cnt <= 0) &&
(divert_info_head->next->usage_cnt <= 0)) {
ib = divert_info_head;
divert_info_head = divert_info_head->next;
kfree(ib);
} else
break;
} /* divert_info_head->next */
spin_unlock_irqrestore(&divert_info_lock, flags);
wake_up_interruptible(&(rd_queue));
} /* put_info_buffer */
#ifdef CONFIG_PROC_FS
/**********************************/
/* deflection device read routine */
/**********************************/
static ssize_t
isdn_divert_read(struct file *file, char __user *buf, size_t count, loff_t *off)
{
struct divert_info *inf;
int len;
if (!(inf = *((struct divert_info **) file->private_data))) {
if (file->f_flags & O_NONBLOCK)
return -EAGAIN;
wait_event_interruptible(rd_queue, (inf =
*((struct divert_info **) file->private_data)));
}
if (!inf)
return (0);
inf->usage_cnt--; /* new usage count */
file->private_data = &inf->next; /* next structure */
if ((len = strlen(inf->info_start)) <= count) {
if (copy_to_user(buf, inf->info_start, len))
return -EFAULT;
*off += len;
return (len);
}
return (0);
} /* isdn_divert_read */
/**********************************/
/* deflection device write routine */
/**********************************/
static ssize_t
isdn_divert_write(struct file *file, const char __user *buf, size_t count, loff_t *off)
{
return (-ENODEV);
} /* isdn_divert_write */
/***************************************/
/* select routines for various kernels */
/***************************************/
static __poll_t
isdn_divert_poll(struct file *file, poll_table *wait)
{
__poll_t mask = 0;
poll_wait(file, &(rd_queue), wait);
/* mask = EPOLLOUT | EPOLLWRNORM; */
if (*((struct divert_info **) file->private_data)) {
mask |= EPOLLIN | EPOLLRDNORM;
}
return mask;
} /* isdn_divert_poll */
/****************/
/* Open routine */
/****************/
static int
isdn_divert_open(struct inode *ino, struct file *filep)
{
unsigned long flags;
spin_lock_irqsave(&divert_info_lock, flags);
if_used++;
if (divert_info_head)
filep->private_data = &(divert_info_tail->next);
else
filep->private_data = &divert_info_head;
spin_unlock_irqrestore(&divert_info_lock, flags);
/* start_divert(); */
return nonseekable_open(ino, filep);
} /* isdn_divert_open */
/*******************/
/* close routine */
/*******************/
static int
isdn_divert_close(struct inode *ino, struct file *filep)
{
struct divert_info *inf;
unsigned long flags;
spin_lock_irqsave(&divert_info_lock, flags);
if_used--;
inf = *((struct divert_info **) filep->private_data);
while (inf) {
inf->usage_cnt--;
inf = inf->next;
}
if (if_used <= 0)
while (divert_info_head) {
inf = divert_info_head;
divert_info_head = divert_info_head->next;
kfree(inf);
}
spin_unlock_irqrestore(&divert_info_lock, flags);
return (0);
} /* isdn_divert_close */
/*********/
/* IOCTL */
/*********/
static int isdn_divert_ioctl_unlocked(struct file *file, uint cmd, ulong arg)
{
divert_ioctl dioctl;
int i;
unsigned long flags;
divert_rule *rulep;
char *cp;
if (copy_from_user(&dioctl, (void __user *) arg, sizeof(dioctl)))
return -EFAULT;
switch (cmd) {
case IIOCGETVER:
dioctl.drv_version = DIVERT_IIOC_VERSION; /* set version */
break;
case IIOCGETDRV:
if ((dioctl.getid.drvid = divert_if.name_to_drv(dioctl.getid.drvnam)) < 0)
return (-EINVAL);
break;
case IIOCGETNAM:
cp = divert_if.drv_to_name(dioctl.getid.drvid);
if (!cp)
return (-EINVAL);
if (!*cp)
return (-EINVAL);
strcpy(dioctl.getid.drvnam, cp);
break;
case IIOCGETRULE:
if (!(rulep = getruleptr(dioctl.getsetrule.ruleidx)))
return (-EINVAL);
dioctl.getsetrule.rule = *rulep; /* copy data */
break;
case IIOCMODRULE:
if (!(rulep = getruleptr(dioctl.getsetrule.ruleidx)))
return (-EINVAL);
spin_lock_irqsave(&divert_lock, flags);
*rulep = dioctl.getsetrule.rule; /* copy data */
spin_unlock_irqrestore(&divert_lock, flags);
return (0); /* no copy required */
break;
case IIOCINSRULE:
return (insertrule(dioctl.getsetrule.ruleidx, &dioctl.getsetrule.rule));
break;
case IIOCDELRULE:
return (deleterule(dioctl.getsetrule.ruleidx));
break;
case IIOCDODFACT:
return (deflect_extern_action(dioctl.fwd_ctrl.subcmd,
dioctl.fwd_ctrl.callid,
dioctl.fwd_ctrl.to_nr));
case IIOCDOCFACT:
case IIOCDOCFDIS:
case IIOCDOCFINT:
if (!divert_if.drv_to_name(dioctl.cf_ctrl.drvid))
return (-EINVAL); /* invalid driver */
if (strnlen(dioctl.cf_ctrl.msn, sizeof(dioctl.cf_ctrl.msn)) ==
sizeof(dioctl.cf_ctrl.msn))
return -EINVAL;
if (strnlen(dioctl.cf_ctrl.fwd_nr, sizeof(dioctl.cf_ctrl.fwd_nr)) ==
sizeof(dioctl.cf_ctrl.fwd_nr))
return -EINVAL;
if ((i = cf_command(dioctl.cf_ctrl.drvid,
(cmd == IIOCDOCFACT) ? 1 : (cmd == IIOCDOCFDIS) ? 0 : 2,
dioctl.cf_ctrl.cfproc,
dioctl.cf_ctrl.msn,
dioctl.cf_ctrl.service,
dioctl.cf_ctrl.fwd_nr,
&dioctl.cf_ctrl.procid)))
return (i);
break;
default:
return (-EINVAL);
} /* switch cmd */
return copy_to_user((void __user *)arg, &dioctl, sizeof(dioctl)) ? -EFAULT : 0;
} /* isdn_divert_ioctl */
static long isdn_divert_ioctl(struct file *file, uint cmd, ulong arg)
{
long ret;
mutex_lock(&isdn_divert_mutex);
ret = isdn_divert_ioctl_unlocked(file, cmd, arg);
mutex_unlock(&isdn_divert_mutex);
return ret;
}
static const struct file_operations isdn_fops =
{
.owner = THIS_MODULE,
.llseek = no_llseek,
.read = isdn_divert_read,
.write = isdn_divert_write,
.poll = isdn_divert_poll,
.unlocked_ioctl = isdn_divert_ioctl,
.open = isdn_divert_open,
.release = isdn_divert_close,
};
/****************************/
/* isdn subdir in /proc/net */
/****************************/
static struct proc_dir_entry *isdn_proc_entry = NULL;
static struct proc_dir_entry *isdn_divert_entry = NULL;
#endif /* CONFIG_PROC_FS */
/***************************************************************************/
/* divert_dev_init must be called before the proc filesystem may be used */
/***************************************************************************/
int
divert_dev_init(void)
{
init_waitqueue_head(&rd_queue);
#ifdef CONFIG_PROC_FS
isdn_proc_entry = proc_mkdir("isdn", init_net.proc_net);
if (!isdn_proc_entry)
return (-1);
isdn_divert_entry = proc_create("divert", S_IFREG | S_IRUGO,
isdn_proc_entry, &isdn_fops);
if (!isdn_divert_entry) {
remove_proc_entry("isdn", init_net.proc_net);
return (-1);
}
#endif /* CONFIG_PROC_FS */
return (0);
} /* divert_dev_init */
/***************************************************************************/
/* divert_dev_deinit must be called before leaving isdn when included as */
/* a module. */
/***************************************************************************/
int
divert_dev_deinit(void)
{
#ifdef CONFIG_PROC_FS
remove_proc_entry("divert", isdn_proc_entry);
remove_proc_entry("isdn", init_net.proc_net);
#endif /* CONFIG_PROC_FS */
return (0);
} /* divert_dev_deinit */
此差异已折叠。
/* $Id: isdn_divert.h,v 1.5.6.1 2001/09/23 22:24:36 kai Exp $
*
* Header for the diversion supplementary ioctl interface.
*
* Copyright 1998 by Werner Cornelius (werner@ikt.de)
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
#include <linux/ioctl.h>
#include <linux/types.h>
/******************************************/
/* IOCTL codes for interface to user prog */
/******************************************/
#define DIVERT_IIOC_VERSION 0x01 /* actual version */
#define IIOCGETVER _IO('I', 1) /* get version of interface */
#define IIOCGETDRV _IO('I', 2) /* get driver number */
#define IIOCGETNAM _IO('I', 3) /* get driver name */
#define IIOCGETRULE _IO('I', 4) /* read one rule */
#define IIOCMODRULE _IO('I', 5) /* modify/replace a rule */
#define IIOCINSRULE _IO('I', 6) /* insert/append one rule */
#define IIOCDELRULE _IO('I', 7) /* delete a rule */
#define IIOCDODFACT _IO('I', 8) /* hangup/reject/alert/immediately deflect a call */
#define IIOCDOCFACT _IO('I', 9) /* activate control forwarding in PBX */
#define IIOCDOCFDIS _IO('I', 10) /* deactivate control forwarding in PBX */
#define IIOCDOCFINT _IO('I', 11) /* interrogate control forwarding in PBX */
/*************************************/
/* states reported through interface */
/*************************************/
#define DEFLECT_IGNORE 0 /* ignore incoming call */
#define DEFLECT_REPORT 1 /* only report */
#define DEFLECT_PROCEED 2 /* deflect when externally triggered */
#define DEFLECT_ALERT 3 /* alert and deflect after delay */
#define DEFLECT_REJECT 4 /* reject immediately */
#define DIVERT_ACTIVATE 5 /* diversion activate */
#define DIVERT_DEACTIVATE 6 /* diversion deactivate */
#define DIVERT_REPORT 7 /* interrogation result */
#define DEFLECT_AUTODEL 255 /* only for internal use */
#define DEFLECT_ALL_IDS 0xFFFFFFFF /* all drivers selected */
typedef struct {
ulong drvid; /* driver ids, bit mapped */
char my_msn[35]; /* desired msn, subaddr allowed */
char caller[35]; /* caller id, partial string with * + subaddr allowed */
char to_nr[35]; /* deflected to number incl. subaddress */
u_char si1, si2; /* service indicators, si1=bitmask, si1+2 0 = all */
u_char screen; /* screening: 0 = no info, 1 = info, 2 = nfo with nr */
u_char callopt; /* option for call handling:
0 = all calls
1 = only non waiting calls
2 = only waiting calls */
u_char action; /* desired action:
0 = don't report call -> ignore
1 = report call, do not allow/proceed for deflection
2 = report call, send proceed, wait max waittime secs
3 = report call, alert and deflect after waittime
4 = report call, reject immediately
actions 1-2 only take place if interface is opened
*/
u_char waittime; /* maximum wait time for proceeding */
} divert_rule;
typedef union {
int drv_version; /* return of driver version */
struct {
int drvid; /* id of driver */
char drvnam[30]; /* name of driver */
} getid;
struct {
int ruleidx; /* index of rule */
divert_rule rule; /* rule parms */
} getsetrule;
struct {
u_char subcmd; /* 0 = hangup/reject,
1 = alert,
2 = deflect */
ulong callid; /* id of call delivered by ascii output */
char to_nr[35]; /* destination when deflect,
else uus1 string (maxlen 31),
data from rule used if empty */
} fwd_ctrl;
struct {
int drvid; /* id of driver */
u_char cfproc; /* cfu = 0, cfb = 1, cfnr = 2 */
ulong procid; /* process id returned when no error */
u_char service; /* basically coded service, 0 = all */
char msn[25]; /* desired msn, empty = all */
char fwd_nr[35];/* forwarded to number + subaddress */
} cf_ctrl;
} divert_ioctl;
#ifdef __KERNEL__
#include <linux/isdnif.h>
#include <linux/isdn_divertif.h>
#define AUTODEL_TIME 30 /* timeout in s to delete internal entries */
/**************************************************/
/* structure keeping ascii info for device output */
/**************************************************/
struct divert_info {
struct divert_info *next;
ulong usage_cnt; /* number of files still to work */
char info_start[2]; /* info string start */
};
/**************/
/* Prototypes */
/**************/
extern spinlock_t divert_lock;
extern ulong if_used; /* number of interface users */
extern int divert_dev_deinit(void);
extern int divert_dev_init(void);
extern void put_info_buffer(char *);
extern int ll_callback(isdn_ctrl *);
extern isdn_divert_if divert_if;
extern divert_rule *getruleptr(int);
extern int insertrule(int, divert_rule *);
extern int deleterule(int);
extern void deleteprocs(void);
extern int deflect_extern_action(u_char, ulong, char *);
extern int cf_command(int, int, u_char, char *, u_char, char *, ulong *);
#endif /* __KERNEL__ */
# SPDX-License-Identifier: GPL-2.0-only
#
# Old ISDN4Linux config
#
if ISDN_I4L
config ISDN_PPP
bool "Support synchronous PPP"
depends on INET
select SLHC
help
Over digital connections such as ISDN, there is no need to
synchronize sender and recipient's clocks with start and stop bits
as is done over analog telephone lines. Instead, one can use
"synchronous PPP". Saying Y here will include this protocol. This
protocol is used by Cisco and Sun for example. So you want to say Y
here if the other end of your ISDN connection supports it. You will
need a special version of pppd (called ipppd) for using this
feature. See <file:Documentation/isdn/README.syncppp> and
<file:Documentation/isdn/syncPPP.FAQ> for more information.
config ISDN_PPP_VJ
bool "Use VJ-compression with synchronous PPP"
depends on ISDN_PPP
help
This enables Van Jacobson header compression for synchronous PPP.
Say Y if the other end of the connection supports it.
config ISDN_MPP
bool "Support generic MP (RFC 1717)"
depends on ISDN_PPP
help
With synchronous PPP enabled, it is possible to increase throughput
by bundling several ISDN-connections, using this protocol. See
<file:Documentation/isdn/README.syncppp> for more information.
config IPPP_FILTER
bool "Filtering for synchronous PPP"
depends on ISDN_PPP
help
Say Y here if you want to be able to filter the packets passing over
IPPP interfaces. This allows you to control which packets count as
activity (i.e. which packets will reset the idle timer or bring up
a demand-dialled link) and which packets are to be dropped entirely.
You need to say Y here if you wish to use the pass-filter and
active-filter options to ipppd.
config ISDN_PPP_BSDCOMP
tristate "Support BSD compression"
depends on ISDN_PPP
help
Support for the BSD-Compress compression method for PPP, which uses
the LZW compression method to compress each PPP packet before it is
sent over the wire. The machine at the other end of the PPP link
(usually your ISP) has to support the BSD-Compress compression
method as well for this to be useful. Even if they don't support it,
it is safe to say Y here.
config ISDN_AUDIO
bool "Support audio via ISDN"
help
If you say Y here, the modem-emulator will support a subset of the
EIA Class 8 Voice commands. Using a getty with voice-support
(mgetty+sendfax by <gert@greenie.muc.de> with an extension, available
with the ISDN utility package for example), you will be able to use
your Linux box as an ISDN-answering machine. Of course, this must be
supported by the lowlevel driver also. Currently, the HiSax driver
is the only voice-supporting driver. See
<file:Documentation/isdn/README.audio> for more information.
config ISDN_TTY_FAX
bool "Support AT-Fax Class 1 and 2 commands"
depends on ISDN_AUDIO
help
If you say Y here, the modem-emulator will support a subset of the
Fax Class 1 and 2 commands. Using a getty with fax-support
(mgetty+sendfax, hylafax), you will be able to use your Linux box as
an ISDN-fax-machine. This must be supported by the lowlevel driver
also. See <file:Documentation/isdn/README.fax> for more information.
config ISDN_X25
bool "X.25 PLP on top of ISDN"
depends on X25
help
This feature provides the X.25 protocol over ISDN connections.
See <file:Documentation/isdn/README.x25> for more information
if you are thinking about using this.
menu "ISDN feature submodules"
config ISDN_DRV_LOOP
tristate "isdnloop support"
depends on BROKEN_ON_SMP
help
This driver provides a virtual ISDN card. Its primary purpose is
testing of linklevel features or configuration without getting
charged by your service-provider for lots of phone calls.
You need will need the loopctrl utility from the latest isdn4k-utils
package to set up this driver.
config ISDN_DIVERSION
tristate "Support isdn diversion services"
help
This option allows you to use some supplementary diversion
services in conjunction with the HiSax driver on an EURO/DSS1
line.
Supported options are CD (call deflection), CFU (Call forward
unconditional), CFB (Call forward when busy) and CFNR (call forward
not reachable). Additionally the actual CFU, CFB and CFNR state may
be interrogated.
The use of CFU, CFB, CFNR and interrogation may be limited to some
countries. The keypad protocol is still not implemented. CD should
work in all countries if the service has been subscribed to.
Please read the file <file:Documentation/isdn/README.diversion>.
endmenu
comment "ISDN4Linux hardware drivers"
# end ISDN_I4L
endif
...@@ -3,18 +3,4 @@ ...@@ -3,18 +3,4 @@
# Each configuration option enables a list of files. # Each configuration option enables a list of files.
obj-$(CONFIG_ISDN_I4L) += isdn.o
obj-$(CONFIG_ISDN_PPP_BSDCOMP) += isdn_bsdcomp.o
obj-$(CONFIG_ISDN_HDLC) += isdnhdlc.o obj-$(CONFIG_ISDN_HDLC) += isdnhdlc.o
# Multipart objects.
isdn-y := isdn_net.o isdn_tty.o isdn_v110.o isdn_common.o
# Optional parts of multipart objects.
isdn-$(CONFIG_ISDN_PPP) += isdn_ppp.o
isdn-$(CONFIG_ISDN_X25) += isdn_concap.o isdn_x25iface.o
isdn-$(CONFIG_ISDN_AUDIO) += isdn_audio.o
isdn-$(CONFIG_ISDN_TTY_FAX) += isdn_ttyfax.o
此差异已折叠。
/* $Id: isdn_audio.h,v 1.1.2.2 2004/01/12 22:37:18 keil Exp $
*
* Linux ISDN subsystem, audio conversion and compression (linklevel).
*
* Copyright 1994-1999 by Fritz Elfert (fritz@isdn4linux.de)
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
#define DTMF_NPOINTS 205 /* Number of samples for DTMF recognition */
typedef struct adpcm_state {
int a;
int d;
int word;
int nleft;
int nbits;
} adpcm_state;
typedef struct dtmf_state {
char last;
char llast;
int idx;
int buf[DTMF_NPOINTS];
} dtmf_state;
typedef struct silence_state {
int state;
unsigned int idx;
} silence_state;
extern void isdn_audio_ulaw2alaw(unsigned char *, unsigned long);
extern void isdn_audio_alaw2ulaw(unsigned char *, unsigned long);
extern adpcm_state *isdn_audio_adpcm_init(adpcm_state *, int);
extern int isdn_audio_adpcm2xlaw(adpcm_state *, int, unsigned char *, unsigned char *, int);
extern int isdn_audio_xlaw2adpcm(adpcm_state *, int, unsigned char *, unsigned char *, int);
extern void isdn_audio_calc_dtmf(modem_info *, unsigned char *, int, int);
extern void isdn_audio_eval_dtmf(modem_info *);
dtmf_state *isdn_audio_dtmf_init(dtmf_state *);
extern void isdn_audio_calc_silence(modem_info *, unsigned char *, int, int);
extern void isdn_audio_eval_silence(modem_info *);
silence_state *isdn_audio_silence_init(silence_state *);
extern void isdn_audio_put_dle_code(modem_info *, u_char);
此差异已折叠。
此差异已折叠。
/* $Id: isdn_common.h,v 1.1.2.2 2004/01/12 22:37:19 keil Exp $
*
* header for Linux ISDN subsystem
* common used functions and debugging-switches (linklevel).
*
* Copyright 1994-1999 by Fritz Elfert (fritz@isdn4linux.de)
* Copyright 1995,96 by Thinking Objects Software GmbH Wuerzburg
* Copyright 1995,96 by Michael Hipp (Michael.Hipp@student.uni-tuebingen.de)
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
#undef ISDN_DEBUG_MODEM_OPEN
#undef ISDN_DEBUG_MODEM_IOCTL
#undef ISDN_DEBUG_MODEM_WAITSENT
#undef ISDN_DEBUG_MODEM_HUP
#undef ISDN_DEBUG_MODEM_ICALL
#undef ISDN_DEBUG_MODEM_DUMP
#undef ISDN_DEBUG_MODEM_VOICE
#undef ISDN_DEBUG_AT
#undef ISDN_DEBUG_NET_DUMP
#undef ISDN_DEBUG_NET_DIAL
#undef ISDN_DEBUG_NET_ICALL
/* Prototypes */
extern void isdn_lock_drivers(void);
extern void isdn_unlock_drivers(void);
extern void isdn_free_channel(int di, int ch, int usage);
extern void isdn_all_eaz(int di, int ch);
extern int isdn_command(isdn_ctrl *);
extern int isdn_dc2minor(int di, int ch);
extern void isdn_info_update(void);
extern char *isdn_map_eaz2msn(char *msn, int di);
extern void isdn_timer_ctrl(int tf, int onoff);
extern void isdn_unexclusive_channel(int di, int ch);
extern int isdn_getnum(char **);
extern int isdn_readbchan(int, int, u_char *, u_char *, int, wait_queue_head_t *);
extern int isdn_readbchan_tty(int, int, struct tty_port *, int);
extern int isdn_get_free_channel(int, int, int, int, int, char *);
extern int isdn_writebuf_skb_stub(int, int, int, struct sk_buff *);
extern int register_isdn(isdn_if *i);
extern int isdn_msncmp(const char *, const char *);
#if defined(ISDN_DEBUG_NET_DUMP) || defined(ISDN_DEBUG_MODEM_DUMP)
extern void isdn_dumppkt(char *, u_char *, int, int);
#endif
/* $Id: isdn_concap.c,v 1.1.2.2 2004/01/12 22:37:19 keil Exp $
*
* Linux ISDN subsystem, protocol encapsulation
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
/* Stuff to support the concap_proto by isdn4linux. isdn4linux - specific
* stuff goes here. Stuff that depends only on the concap protocol goes to
* another -- protocol specific -- source file.
*
*/
#include <linux/isdn.h>
#include "isdn_x25iface.h"
#include "isdn_net.h"
#include <linux/concap.h>
#include "isdn_concap.h"
/* The following set of device service operations are for encapsulation
protocols that require for reliable datalink semantics. That means:
- before any data is to be submitted the connection must explicitly
be set up.
- after the successful set up of the connection is signalled the
connection is considered to be reliably up.
Auto-dialing ist not compatible with this requirements. Thus, auto-dialing
is completely bypassed.
It might be possible to implement a (non standardized) datalink protocol
that provides a reliable data link service while using some auto dialing
mechanism. Such a protocol would need an auxiliary channel (i.e. user-user-
signaling on the D-channel) while the B-channel is down.
*/
static int isdn_concap_dl_data_req(struct concap_proto *concap, struct sk_buff *skb)
{
struct net_device *ndev = concap->net_dev;
isdn_net_dev *nd = ((isdn_net_local *) netdev_priv(ndev))->netdev;
isdn_net_local *lp = isdn_net_get_locked_lp(nd);
IX25DEBUG("isdn_concap_dl_data_req: %s \n", concap->net_dev->name);
if (!lp) {
IX25DEBUG("isdn_concap_dl_data_req: %s : isdn_net_send_skb returned %d\n", concap->net_dev->name, 1);
return 1;
}
lp->huptimer = 0;
isdn_net_writebuf_skb(lp, skb);
spin_unlock_bh(&lp->xmit_lock);
IX25DEBUG("isdn_concap_dl_data_req: %s : isdn_net_send_skb returned %d\n", concap->net_dev->name, 0);
return 0;
}
static int isdn_concap_dl_connect_req(struct concap_proto *concap)
{
struct net_device *ndev = concap->net_dev;
isdn_net_local *lp = netdev_priv(ndev);
int ret;
IX25DEBUG("isdn_concap_dl_connect_req: %s \n", ndev->name);
/* dial ... */
ret = isdn_net_dial_req(lp);
if (ret) IX25DEBUG("dialing failed\n");
return ret;
}
static int isdn_concap_dl_disconn_req(struct concap_proto *concap)
{
IX25DEBUG("isdn_concap_dl_disconn_req: %s \n", concap->net_dev->name);
isdn_net_hangup(concap->net_dev);
return 0;
}
struct concap_device_ops isdn_concap_reliable_dl_dops = {
.data_req = &isdn_concap_dl_data_req,
.connect_req = &isdn_concap_dl_connect_req,
.disconn_req = &isdn_concap_dl_disconn_req
};
/* The following should better go into a dedicated source file such that
this sourcefile does not need to include any protocol specific header
files. For now:
*/
struct concap_proto *isdn_concap_new(int encap)
{
switch (encap) {
case ISDN_NET_ENCAP_X25IFACE:
return isdn_x25iface_proto_new();
}
return NULL;
}
/* $Id: isdn_concap.h,v 1.1.2.2 2004/01/12 22:37:19 keil Exp $
*
* Linux ISDN subsystem, protocol encapsulation
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
extern struct concap_device_ops isdn_concap_reliable_dl_dops;
extern struct concap_proto *isdn_concap_new(int);
此差异已折叠。
/* $Id: isdn_net.h,v 1.1.2.2 2004/01/12 22:37:19 keil Exp $
*
* header for Linux ISDN subsystem, network related functions (linklevel).
*
* Copyright 1994-1999 by Fritz Elfert (fritz@isdn4linux.de)
* Copyright 1995,96 by Thinking Objects Software GmbH Wuerzburg
* Copyright 1995,96 by Michael Hipp (Michael.Hipp@student.uni-tuebingen.de)
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
/* Definitions for hupflags: */
#define ISDN_WAITCHARGE 1 /* did not get a charge info yet */
#define ISDN_HAVECHARGE 2 /* We know a charge info */
#define ISDN_CHARGEHUP 4 /* We want to use the charge mechanism */
#define ISDN_INHUP 8 /* Even if incoming, close after huptimeout */
#define ISDN_MANCHARGE 16 /* Charge Interval manually set */
/*
* Definitions for Cisco-HDLC header.
*/
#define CISCO_ADDR_UNICAST 0x0f
#define CISCO_ADDR_BROADCAST 0x8f
#define CISCO_CTRL 0x00
#define CISCO_TYPE_CDP 0x2000
#define CISCO_TYPE_SLARP 0x8035
#define CISCO_SLARP_REQUEST 0
#define CISCO_SLARP_REPLY 1
#define CISCO_SLARP_KEEPALIVE 2
extern char *isdn_net_new(char *, struct net_device *);
extern char *isdn_net_newslave(char *);
extern int isdn_net_rm(char *);
extern int isdn_net_rmall(void);
extern int isdn_net_stat_callback(int, isdn_ctrl *);
extern int isdn_net_setcfg(isdn_net_ioctl_cfg *);
extern int isdn_net_getcfg(isdn_net_ioctl_cfg *);
extern int isdn_net_addphone(isdn_net_ioctl_phone *);
extern int isdn_net_getphones(isdn_net_ioctl_phone *, char __user *);
extern int isdn_net_getpeer(isdn_net_ioctl_phone *, isdn_net_ioctl_phone __user *);
extern int isdn_net_delphone(isdn_net_ioctl_phone *);
extern int isdn_net_find_icall(int, int, int, setup_parm *);
extern void isdn_net_hangup(struct net_device *);
extern void isdn_net_dial(void);
extern void isdn_net_autohup(void);
extern int isdn_net_force_hangup(char *);
extern int isdn_net_force_dial(char *);
extern isdn_net_dev *isdn_net_findif(char *);
extern int isdn_net_rcv_skb(int, struct sk_buff *);
extern int isdn_net_dial_req(isdn_net_local *);
extern void isdn_net_writebuf_skb(isdn_net_local *lp, struct sk_buff *skb);
extern void isdn_net_write_super(isdn_net_local *lp, struct sk_buff *skb);
#define ISDN_NET_MAX_QUEUE_LENGTH 2
#define ISDN_MASTER_PRIV(lp) ((isdn_net_local *) netdev_priv(lp->master))
#define ISDN_SLAVE_PRIV(lp) ((isdn_net_local *) netdev_priv(lp->slave))
#define MASTER_TO_SLAVE(master) \
(((isdn_net_local *) netdev_priv(master))->slave)
/*
* is this particular channel busy?
*/
static __inline__ int isdn_net_lp_busy(isdn_net_local *lp)
{
if (atomic_read(&lp->frame_cnt) < ISDN_NET_MAX_QUEUE_LENGTH)
return 0;
else
return 1;
}
/*
* For the given net device, this will get a non-busy channel out of the
* corresponding bundle. The returned channel is locked.
*/
static __inline__ isdn_net_local *isdn_net_get_locked_lp(isdn_net_dev *nd)
{
unsigned long flags;
isdn_net_local *lp;
spin_lock_irqsave(&nd->queue_lock, flags);
lp = nd->queue; /* get lp on top of queue */
while (isdn_net_lp_busy(nd->queue)) {
nd->queue = nd->queue->next;
if (nd->queue == lp) { /* not found -- should never happen */
lp = NULL;
goto errout;
}
}
lp = nd->queue;
nd->queue = nd->queue->next;
spin_unlock_irqrestore(&nd->queue_lock, flags);
spin_lock(&lp->xmit_lock);
local_bh_disable();
return lp;
errout:
spin_unlock_irqrestore(&nd->queue_lock, flags);
return lp;
}
/*
* add a channel to a bundle
*/
static __inline__ void isdn_net_add_to_bundle(isdn_net_dev *nd, isdn_net_local *nlp)
{
isdn_net_local *lp;
unsigned long flags;
spin_lock_irqsave(&nd->queue_lock, flags);
lp = nd->queue;
// printk(KERN_DEBUG "%s: lp:%s(%p) nlp:%s(%p) last(%p)\n",
// __func__, lp->name, lp, nlp->name, nlp, lp->last);
nlp->last = lp->last;
lp->last->next = nlp;
lp->last = nlp;
nlp->next = lp;
nd->queue = nlp;
spin_unlock_irqrestore(&nd->queue_lock, flags);
}
/*
* remove a channel from the bundle it belongs to
*/
static __inline__ void isdn_net_rm_from_bundle(isdn_net_local *lp)
{
isdn_net_local *master_lp = lp;
unsigned long flags;
if (lp->master)
master_lp = ISDN_MASTER_PRIV(lp);
// printk(KERN_DEBUG "%s: lp:%s(%p) mlp:%s(%p) last(%p) next(%p) mndq(%p)\n",
// __func__, lp->name, lp, master_lp->name, master_lp, lp->last, lp->next, master_lp->netdev->queue);
spin_lock_irqsave(&master_lp->netdev->queue_lock, flags);
lp->last->next = lp->next;
lp->next->last = lp->last;
if (master_lp->netdev->queue == lp) {
master_lp->netdev->queue = lp->next;
if (lp->next == lp) { /* last in queue */
master_lp->netdev->queue = master_lp->netdev->local;
}
}
lp->next = lp->last = lp; /* (re)set own pointers */
// printk(KERN_DEBUG "%s: mndq(%p)\n",
// __func__, master_lp->netdev->queue);
spin_unlock_irqrestore(&master_lp->netdev->queue_lock, flags);
}
此差异已折叠。
/* $Id: isdn_ppp.h,v 1.1.2.2 2004/01/12 22:37:19 keil Exp $
*
* header for Linux ISDN subsystem, functions for synchronous PPP (linklevel).
*
* Copyright 1995,96 by Michael Hipp (Michael.Hipp@student.uni-tuebingen.de)
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
#include <linux/ppp_defs.h> /* for PPP_PROTOCOL */
#include <linux/isdn_ppp.h> /* for isdn_ppp info */
extern int isdn_ppp_read(int, struct file *, char __user *, int);
extern int isdn_ppp_write(int, struct file *, const char __user *, int);
extern int isdn_ppp_open(int, struct file *);
extern int isdn_ppp_init(void);
extern void isdn_ppp_cleanup(void);
extern int isdn_ppp_free(isdn_net_local *);
extern int isdn_ppp_bind(isdn_net_local *);
extern int isdn_ppp_autodial_filter(struct sk_buff *, isdn_net_local *);
extern int isdn_ppp_xmit(struct sk_buff *, struct net_device *);
extern void isdn_ppp_receive(isdn_net_dev *, isdn_net_local *, struct sk_buff *);
extern int isdn_ppp_dev_ioctl(struct net_device *, struct ifreq *, int);
extern __poll_t isdn_ppp_poll(struct file *, struct poll_table_struct *);
extern int isdn_ppp_ioctl(int, struct file *, unsigned int, unsigned long);
extern void isdn_ppp_release(int, struct file *);
extern int isdn_ppp_dial_slave(char *);
extern void isdn_ppp_wakeup_daemon(isdn_net_local *);
extern int isdn_ppp_register_compressor(struct isdn_ppp_compressor *ipc);
extern int isdn_ppp_unregister_compressor(struct isdn_ppp_compressor *ipc);
#define IPPP_OPEN 0x01
#define IPPP_CONNECT 0x02
#define IPPP_CLOSEWAIT 0x04
#define IPPP_NOBLOCK 0x08
#define IPPP_ASSIGNED 0x10
#define IPPP_MAX_HEADER 10
此差异已折叠。
/* $Id: isdn_tty.h,v 1.1.2.2 2004/01/12 22:37:19 keil Exp $
*
* header for Linux ISDN subsystem, tty related functions (linklevel).
*
* Copyright 1994-1999 by Fritz Elfert (fritz@isdn4linux.de)
* Copyright 1995,96 by Thinking Objects Software GmbH Wuerzburg
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
#define DLE 0x10
#define ETX 0x03
#define DC4 0x14
/*
* Definition of some special Registers of AT-Emulator
*/
#define REG_RINGATA 0
#define REG_RINGCNT 1 /* ring counter register */
#define REG_ESC 2
#define REG_CR 3
#define REG_LF 4
#define REG_BS 5
#define REG_WAITC 7
#define REG_RESP 12 /* show response messages register */
#define BIT_RESP 1 /* show response messages bit */
#define REG_RESPNUM 12 /* show numeric responses register */
#define BIT_RESPNUM 2 /* show numeric responses bit */
#define REG_ECHO 12
#define BIT_ECHO 4
#define REG_DCD 12
#define BIT_DCD 8
#define REG_CTS 12
#define BIT_CTS 16
#define REG_DTRR 12
#define BIT_DTRR 32
#define REG_DSR 12
#define BIT_DSR 64
#define REG_CPPP 12
#define BIT_CPPP 128
#define REG_DXMT 13
#define BIT_DXMT 1
#define REG_T70 13
#define BIT_T70 2
#define BIT_T70_EXT 32
#define REG_DTRHUP 13
#define BIT_DTRHUP 4
#define REG_RESPXT 13
#define BIT_RESPXT 8
#define REG_CIDONCE 13
#define BIT_CIDONCE 16
#define REG_RUNG 13 /* show RUNG message register */
#define BIT_RUNG 64 /* show RUNG message bit */
#define REG_DISPLAY 13
#define BIT_DISPLAY 128
#define REG_L2PROT 14
#define REG_L3PROT 15
#define REG_PSIZE 16
#define REG_WSIZE 17
#define REG_SI1 18
#define REG_SI2 19
#define REG_SI1I 20
#define REG_PLAN 21
#define REG_SCREEN 22
#define REG_CPN 23
#define BIT_CPN 1
#define REG_CPNFCON 23
#define BIT_CPNFCON 2
#define REG_CDN 23
#define BIT_CDN 4
/* defines for result codes */
#define RESULT_OK 0
#define RESULT_CONNECT 1
#define RESULT_RING 2
#define RESULT_NO_CARRIER 3
#define RESULT_ERROR 4
#define RESULT_CONNECT64000 5
#define RESULT_NO_DIALTONE 6
#define RESULT_BUSY 7
#define RESULT_NO_ANSWER 8
#define RESULT_RINGING 9
#define RESULT_NO_MSN_EAZ 10
#define RESULT_VCON 11
#define RESULT_RUNG 12
#define TTY_IS_FCLASS1(info) \
((info->emu.mdmreg[REG_L2PROT] == ISDN_PROTO_L2_FAX) && \
(info->emu.mdmreg[REG_L3PROT] == ISDN_PROTO_L3_FCLASS1))
#define TTY_IS_FCLASS2(info) \
((info->emu.mdmreg[REG_L2PROT] == ISDN_PROTO_L2_FAX) && \
(info->emu.mdmreg[REG_L3PROT] == ISDN_PROTO_L3_FCLASS2))
extern void isdn_tty_modem_escape(void);
extern void isdn_tty_modem_ring(void);
extern void isdn_tty_carrier_timeout(void);
extern void isdn_tty_modem_xmit(void);
extern int isdn_tty_modem_init(void);
extern void isdn_tty_exit(void);
extern void isdn_tty_readmodem(void);
extern int isdn_tty_find_icall(int, int, setup_parm *);
extern int isdn_tty_stat_callback(int, isdn_ctrl *);
extern int isdn_tty_rcv_skb(int, int, int, struct sk_buff *);
extern int isdn_tty_capi_facility(capi_msg *cm);
extern void isdn_tty_at_cout(char *, modem_info *);
extern void isdn_tty_modem_hup(modem_info *, int);
#ifdef CONFIG_ISDN_TTY_FAX
extern int isdn_tty_cmd_PLUSF_FAX(char **, modem_info *);
extern int isdn_tty_fax_command(modem_info *, isdn_ctrl *);
extern void isdn_tty_fax_bitorder(modem_info *, struct sk_buff *);
#endif
此差异已折叠。
/* $Id: isdn_ttyfax.h,v 1.1.2.2 2004/01/12 22:37:19 keil Exp $
*
* header for Linux ISDN subsystem, tty_fax related functions (linklevel).
*
* Copyright 1999 by Armin Schindler (mac@melware.de)
* Copyright 1999 by Ralf Spachmann (mel@melware.de)
* Copyright 1999 by Cytronics & Melware
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
#define XON 0x11
#define XOFF 0x13
#define DC2 0x12
此差异已折叠。
/* $Id: isdn_v110.h,v 1.1.2.2 2004/01/12 22:37:19 keil Exp $
*
* Linux ISDN subsystem, V.110 related functions (linklevel).
*
* Copyright by Thomas Pfeiffer (pfeiffer@pds.de)
*
* This software may be used and distributed according to the terms
* of the GNU General Public License, incorporated herein by reference.
*
*/
#ifndef _isdn_v110_h_
#define _isdn_v110_h_
/*
* isdn_v110_encode will take raw data and encode it using V.110
*/
extern struct sk_buff *isdn_v110_encode(isdn_v110_stream *, struct sk_buff *);
/*
* isdn_v110_decode receives V.110 coded data from the stream and rebuilds
* frames from them. The source stream doesn't need to be framed.
*/
extern struct sk_buff *isdn_v110_decode(isdn_v110_stream *, struct sk_buff *);
extern int isdn_v110_stat_callback(int, isdn_ctrl *);
extern void isdn_v110_close(isdn_v110_stream *v);
#endif
此差异已折叠。
此差异已折叠。
# SPDX-License-Identifier: GPL-2.0-only
# Makefile for the isdnloop ISDN device driver
# Each configuration option enables a list of files.
obj-$(CONFIG_ISDN_DRV_LOOP) += isdnloop.o
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
/* SPDX-License-Identifier: GPL-2.0 */
/*
* wanrouter.h Legacy declarations kept around until X25 is removed
*/
#ifndef _ROUTER_H
#define _ROUTER_H
#include <uapi/linux/wanrouter.h>
#endif /* _ROUTER_H */
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册