1 // SPDX-License-Identifier: GPL-2.0-only
2 /* net/atm/common.c - ATM sockets (common part for PVC and SVC) */
4 /* Written 1995-2000 by Werner Almesberger, EPFL LRC/ICA */
6 #define pr_fmt(fmt) KBUILD_MODNAME ":%s: " fmt, __func__
8 #include <linux/module.h>
9 #include <linux/kmod.h>
10 #include <linux/net.h> /* struct socket, struct proto_ops */
11 #include <linux/atm.h> /* ATM stuff */
12 #include <linux/atmdev.h>
13 #include <linux/socket.h> /* SOL_SOCKET */
14 #include <linux/errno.h> /* error codes */
15 #include <linux/capability.h>
17 #include <linux/sched/signal.h>
18 #include <linux/time64.h> /* 64-bit time for seconds */
19 #include <linux/skbuff.h>
20 #include <linux/bitops.h>
21 #include <linux/init.h>
22 #include <linux/slab.h>
23 #include <net/sock.h> /* struct sock */
24 #include <linux/uaccess.h>
25 #include <linux/poll.h>
27 #include <linux/atomic.h>
29 #include "resources.h" /* atm_find_dev */
30 #include "common.h" /* prototypes */
31 #include "protocols.h" /* atm_init_<transport> */
32 #include "addr.h" /* address registry */
33 #include "signaling.h" /* for WAITING and sigd_attach */
35 struct hlist_head vcc_hash
[VCC_HTABLE_SIZE
];
36 EXPORT_SYMBOL(vcc_hash
);
38 DEFINE_RWLOCK(vcc_sklist_lock
);
39 EXPORT_SYMBOL(vcc_sklist_lock
);
41 static ATOMIC_NOTIFIER_HEAD(atm_dev_notify_chain
);
43 static void __vcc_insert_socket(struct sock
*sk
)
45 struct atm_vcc
*vcc
= atm_sk(sk
);
46 struct hlist_head
*head
= &vcc_hash
[vcc
->vci
& (VCC_HTABLE_SIZE
- 1)];
47 sk
->sk_hash
= vcc
->vci
& (VCC_HTABLE_SIZE
- 1);
48 sk_add_node(sk
, head
);
51 void vcc_insert_socket(struct sock
*sk
)
53 write_lock_irq(&vcc_sklist_lock
);
54 __vcc_insert_socket(sk
);
55 write_unlock_irq(&vcc_sklist_lock
);
57 EXPORT_SYMBOL(vcc_insert_socket
);
59 static void vcc_remove_socket(struct sock
*sk
)
61 write_lock_irq(&vcc_sklist_lock
);
63 write_unlock_irq(&vcc_sklist_lock
);
66 static bool vcc_tx_ready(struct atm_vcc
*vcc
, unsigned int size
)
68 struct sock
*sk
= sk_atm(vcc
);
70 if (sk_wmem_alloc_get(sk
) && !atm_may_send(vcc
, size
)) {
71 pr_debug("Sorry: wmem_alloc = %d, size = %d, sndbuf = %d\n",
72 sk_wmem_alloc_get(sk
), size
, sk
->sk_sndbuf
);
78 static void vcc_sock_destruct(struct sock
*sk
)
80 if (atomic_read(&sk
->sk_rmem_alloc
))
81 printk(KERN_DEBUG
"%s: rmem leakage (%d bytes) detected.\n",
82 __func__
, atomic_read(&sk
->sk_rmem_alloc
));
84 if (refcount_read(&sk
->sk_wmem_alloc
))
85 printk(KERN_DEBUG
"%s: wmem leakage (%d bytes) detected.\n",
86 __func__
, refcount_read(&sk
->sk_wmem_alloc
));
89 static void vcc_def_wakeup(struct sock
*sk
)
94 wq
= rcu_dereference(sk
->sk_wq
);
95 if (skwq_has_sleeper(wq
))
100 static inline int vcc_writable(struct sock
*sk
)
102 struct atm_vcc
*vcc
= atm_sk(sk
);
104 return (vcc
->qos
.txtp
.max_sdu
+
105 refcount_read(&sk
->sk_wmem_alloc
)) <= sk
->sk_sndbuf
;
108 static void vcc_write_space(struct sock
*sk
)
110 struct socket_wq
*wq
;
114 if (vcc_writable(sk
)) {
115 wq
= rcu_dereference(sk
->sk_wq
);
116 if (skwq_has_sleeper(wq
))
117 wake_up_interruptible(&wq
->wait
);
119 sk_wake_async_rcu(sk
, SOCK_WAKE_SPACE
, POLL_OUT
);
125 static void vcc_release_cb(struct sock
*sk
)
127 struct atm_vcc
*vcc
= atm_sk(sk
);
130 vcc
->release_cb(vcc
);
133 static struct proto vcc_proto
= {
135 .owner
= THIS_MODULE
,
136 .obj_size
= sizeof(struct atm_vcc
),
137 .release_cb
= vcc_release_cb
,
140 int vcc_create(struct net
*net
, struct socket
*sock
, int protocol
, int family
, int kern
)
146 if (sock
->type
== SOCK_STREAM
)
148 sk
= sk_alloc(net
, family
, GFP_KERNEL
, &vcc_proto
, kern
);
151 sock_init_data(sock
, sk
);
152 sk
->sk_state_change
= vcc_def_wakeup
;
153 sk
->sk_write_space
= vcc_write_space
;
157 memset(&vcc
->local
, 0, sizeof(struct sockaddr_atmsvc
));
158 memset(&vcc
->remote
, 0, sizeof(struct sockaddr_atmsvc
));
159 vcc
->qos
.txtp
.max_sdu
= 1 << 16; /* for meta VCs */
160 refcount_set(&sk
->sk_wmem_alloc
, 1);
161 atomic_set(&sk
->sk_rmem_alloc
, 0);
165 vcc
->push_oam
= NULL
;
166 vcc
->release_cb
= NULL
;
167 vcc
->vpi
= vcc
->vci
= 0; /* no VCI/VPI yet */
168 vcc
->atm_options
= vcc
->aal_options
= 0;
169 sk
->sk_destruct
= vcc_sock_destruct
;
173 static void vcc_destroy_socket(struct sock
*sk
)
175 struct atm_vcc
*vcc
= atm_sk(sk
);
178 set_bit(ATM_VF_CLOSE
, &vcc
->flags
);
179 clear_bit(ATM_VF_READY
, &vcc
->flags
);
180 if (vcc
->dev
&& vcc
->dev
->ops
->close
)
181 vcc
->dev
->ops
->close(vcc
);
183 vcc
->push(vcc
, NULL
); /* atmarpd has no push */
184 module_put(vcc
->owner
);
186 while ((skb
= skb_dequeue(&sk
->sk_receive_queue
)) != NULL
) {
187 atm_return(vcc
, skb
->truesize
);
191 if (vcc
->dev
&& vcc
->dev
->ops
->owner
) {
192 module_put(vcc
->dev
->ops
->owner
);
193 atm_dev_put(vcc
->dev
);
196 vcc_remove_socket(sk
);
199 int vcc_release(struct socket
*sock
)
201 struct sock
*sk
= sock
->sk
;
205 vcc_destroy_socket(sock
->sk
);
213 void vcc_release_async(struct atm_vcc
*vcc
, int reply
)
215 struct sock
*sk
= sk_atm(vcc
);
217 set_bit(ATM_VF_CLOSE
, &vcc
->flags
);
218 sk
->sk_shutdown
|= RCV_SHUTDOWN
;
220 clear_bit(ATM_VF_WAITING
, &vcc
->flags
);
221 sk
->sk_state_change(sk
);
223 EXPORT_SYMBOL(vcc_release_async
);
225 void vcc_process_recv_queue(struct atm_vcc
*vcc
)
227 struct sk_buff_head queue
, *rq
;
228 struct sk_buff
*skb
, *tmp
;
231 __skb_queue_head_init(&queue
);
232 rq
= &sk_atm(vcc
)->sk_receive_queue
;
234 spin_lock_irqsave(&rq
->lock
, flags
);
235 skb_queue_splice_init(rq
, &queue
);
236 spin_unlock_irqrestore(&rq
->lock
, flags
);
238 skb_queue_walk_safe(&queue
, skb
, tmp
) {
239 __skb_unlink(skb
, &queue
);
243 EXPORT_SYMBOL(vcc_process_recv_queue
);
245 void atm_dev_signal_change(struct atm_dev
*dev
, char signal
)
247 pr_debug("%s signal=%d dev=%p number=%d dev->signal=%d\n",
248 __func__
, signal
, dev
, dev
->number
, dev
->signal
);
250 /* atm driver sending invalid signal */
251 WARN_ON(signal
< ATM_PHY_SIG_LOST
|| signal
> ATM_PHY_SIG_FOUND
);
253 if (dev
->signal
== signal
)
254 return; /* no change */
256 dev
->signal
= signal
;
258 atomic_notifier_call_chain(&atm_dev_notify_chain
, signal
, dev
);
260 EXPORT_SYMBOL(atm_dev_signal_change
);
262 void atm_dev_release_vccs(struct atm_dev
*dev
)
266 write_lock_irq(&vcc_sklist_lock
);
267 for (i
= 0; i
< VCC_HTABLE_SIZE
; i
++) {
268 struct hlist_head
*head
= &vcc_hash
[i
];
269 struct hlist_node
*tmp
;
273 sk_for_each_safe(s
, tmp
, head
) {
275 if (vcc
->dev
== dev
) {
276 vcc_release_async(vcc
, -EPIPE
);
281 write_unlock_irq(&vcc_sklist_lock
);
283 EXPORT_SYMBOL(atm_dev_release_vccs
);
285 static int adjust_tp(struct atm_trafprm
*tp
, unsigned char aal
)
289 if (!tp
->traffic_class
)
293 max_sdu
= ATM_CELL_SIZE
-1;
296 max_sdu
= ATM_MAX_AAL34_PDU
;
299 pr_warn("AAL problems ... (%d)\n", aal
);
302 max_sdu
= ATM_MAX_AAL5_PDU
;
305 tp
->max_sdu
= max_sdu
;
306 else if (tp
->max_sdu
> max_sdu
)
309 tp
->max_cdv
= ATM_MAX_CDV
;
313 static int check_ci(const struct atm_vcc
*vcc
, short vpi
, int vci
)
315 struct hlist_head
*head
= &vcc_hash
[vci
& (VCC_HTABLE_SIZE
- 1)];
317 struct atm_vcc
*walk
;
319 sk_for_each(s
, head
) {
321 if (walk
->dev
!= vcc
->dev
)
323 if (test_bit(ATM_VF_ADDR
, &walk
->flags
) && walk
->vpi
== vpi
&&
324 walk
->vci
== vci
&& ((walk
->qos
.txtp
.traffic_class
!=
325 ATM_NONE
&& vcc
->qos
.txtp
.traffic_class
!= ATM_NONE
) ||
326 (walk
->qos
.rxtp
.traffic_class
!= ATM_NONE
&&
327 vcc
->qos
.rxtp
.traffic_class
!= ATM_NONE
)))
331 /* allow VCCs with same VPI/VCI iff they don't collide on
332 TX/RX (but we may refuse such sharing for other reasons,
333 e.g. if protocol requires to have both channels) */
338 static int find_ci(const struct atm_vcc
*vcc
, short *vpi
, int *vci
)
340 static short p
; /* poor man's per-device cache */
346 if (*vpi
!= ATM_VPI_ANY
&& *vci
!= ATM_VCI_ANY
) {
347 err
= check_ci(vcc
, *vpi
, *vci
);
350 /* last scan may have left values out of bounds for current device */
351 if (*vpi
!= ATM_VPI_ANY
)
353 else if (p
>= 1 << vcc
->dev
->ci_range
.vpi_bits
)
355 if (*vci
!= ATM_VCI_ANY
)
357 else if (c
< ATM_NOT_RSV_VCI
|| c
>= 1 << vcc
->dev
->ci_range
.vci_bits
)
362 if (!check_ci(vcc
, p
, c
)) {
367 if (*vci
== ATM_VCI_ANY
) {
369 if (c
>= 1 << vcc
->dev
->ci_range
.vci_bits
)
372 if ((c
== ATM_NOT_RSV_VCI
|| *vci
!= ATM_VCI_ANY
) &&
373 *vpi
== ATM_VPI_ANY
) {
375 if (p
>= 1 << vcc
->dev
->ci_range
.vpi_bits
)
378 } while (old_p
!= p
|| old_c
!= c
);
382 static int __vcc_connect(struct atm_vcc
*vcc
, struct atm_dev
*dev
, short vpi
,
385 struct sock
*sk
= sk_atm(vcc
);
388 if ((vpi
!= ATM_VPI_UNSPEC
&& vpi
!= ATM_VPI_ANY
&&
389 vpi
>> dev
->ci_range
.vpi_bits
) || (vci
!= ATM_VCI_UNSPEC
&&
390 vci
!= ATM_VCI_ANY
&& vci
>> dev
->ci_range
.vci_bits
))
392 if (vci
> 0 && vci
< ATM_NOT_RSV_VCI
&& !capable(CAP_NET_BIND_SERVICE
))
395 if (!try_module_get(dev
->ops
->owner
))
398 write_lock_irq(&vcc_sklist_lock
);
399 if (test_bit(ATM_DF_REMOVED
, &dev
->flags
) ||
400 (error
= find_ci(vcc
, &vpi
, &vci
))) {
401 write_unlock_irq(&vcc_sklist_lock
);
402 goto fail_module_put
;
406 __vcc_insert_socket(sk
);
407 write_unlock_irq(&vcc_sklist_lock
);
408 switch (vcc
->qos
.aal
) {
410 error
= atm_init_aal0(vcc
);
411 vcc
->stats
= &dev
->stats
.aal0
;
414 error
= atm_init_aal34(vcc
);
415 vcc
->stats
= &dev
->stats
.aal34
;
418 /* ATM_AAL5 is also used in the "0 for default" case */
419 vcc
->qos
.aal
= ATM_AAL5
;
422 error
= atm_init_aal5(vcc
);
423 vcc
->stats
= &dev
->stats
.aal5
;
429 error
= adjust_tp(&vcc
->qos
.txtp
, vcc
->qos
.aal
);
431 error
= adjust_tp(&vcc
->qos
.rxtp
, vcc
->qos
.aal
);
434 pr_debug("VCC %d.%d, AAL %d\n", vpi
, vci
, vcc
->qos
.aal
);
435 pr_debug(" TX: %d, PCR %d..%d, SDU %d\n",
436 vcc
->qos
.txtp
.traffic_class
,
437 vcc
->qos
.txtp
.min_pcr
,
438 vcc
->qos
.txtp
.max_pcr
,
439 vcc
->qos
.txtp
.max_sdu
);
440 pr_debug(" RX: %d, PCR %d..%d, SDU %d\n",
441 vcc
->qos
.rxtp
.traffic_class
,
442 vcc
->qos
.rxtp
.min_pcr
,
443 vcc
->qos
.rxtp
.max_pcr
,
444 vcc
->qos
.rxtp
.max_sdu
);
446 if (dev
->ops
->open
) {
447 error
= dev
->ops
->open(vcc
);
454 vcc_remove_socket(sk
);
456 module_put(dev
->ops
->owner
);
457 /* ensure we get dev module ref count correct */
462 int vcc_connect(struct socket
*sock
, int itf
, short vpi
, int vci
)
465 struct atm_vcc
*vcc
= ATM_SD(sock
);
468 pr_debug("(vpi %d, vci %d)\n", vpi
, vci
);
469 if (sock
->state
== SS_CONNECTED
)
471 if (sock
->state
!= SS_UNCONNECTED
)
476 if (vpi
!= ATM_VPI_UNSPEC
&& vci
!= ATM_VCI_UNSPEC
)
477 clear_bit(ATM_VF_PARTIAL
, &vcc
->flags
);
479 if (test_bit(ATM_VF_PARTIAL
, &vcc
->flags
))
481 pr_debug("(TX: cl %d,bw %d-%d,sdu %d; "
482 "RX: cl %d,bw %d-%d,sdu %d,AAL %s%d)\n",
483 vcc
->qos
.txtp
.traffic_class
, vcc
->qos
.txtp
.min_pcr
,
484 vcc
->qos
.txtp
.max_pcr
, vcc
->qos
.txtp
.max_sdu
,
485 vcc
->qos
.rxtp
.traffic_class
, vcc
->qos
.rxtp
.min_pcr
,
486 vcc
->qos
.rxtp
.max_pcr
, vcc
->qos
.rxtp
.max_sdu
,
487 vcc
->qos
.aal
== ATM_AAL5
? "" :
488 vcc
->qos
.aal
== ATM_AAL0
? "" : " ??? code ",
489 vcc
->qos
.aal
== ATM_AAL0
? 0 : vcc
->qos
.aal
);
490 if (!test_bit(ATM_VF_HASQOS
, &vcc
->flags
))
492 if (vcc
->qos
.txtp
.traffic_class
== ATM_ANYCLASS
||
493 vcc
->qos
.rxtp
.traffic_class
== ATM_ANYCLASS
)
495 if (likely(itf
!= ATM_ITF_ANY
)) {
496 dev
= try_then_request_module(atm_dev_lookup(itf
),
497 "atm-device-%d", itf
);
500 mutex_lock(&atm_dev_mutex
);
501 if (!list_empty(&atm_devs
)) {
502 dev
= list_entry(atm_devs
.next
,
503 struct atm_dev
, dev_list
);
506 mutex_unlock(&atm_dev_mutex
);
510 error
= __vcc_connect(vcc
, dev
, vpi
, vci
);
515 if (vpi
== ATM_VPI_UNSPEC
|| vci
== ATM_VCI_UNSPEC
)
516 set_bit(ATM_VF_PARTIAL
, &vcc
->flags
);
517 if (test_bit(ATM_VF_READY
, &ATM_SD(sock
)->flags
))
518 sock
->state
= SS_CONNECTED
;
522 int vcc_recvmsg(struct socket
*sock
, struct msghdr
*msg
, size_t size
,
525 struct sock
*sk
= sock
->sk
;
528 int copied
, error
= -EINVAL
;
530 if (sock
->state
!= SS_CONNECTED
)
533 /* only handle MSG_DONTWAIT and MSG_PEEK */
534 if (flags
& ~(MSG_DONTWAIT
| MSG_PEEK
))
538 if (test_bit(ATM_VF_RELEASED
, &vcc
->flags
) ||
539 test_bit(ATM_VF_CLOSE
, &vcc
->flags
) ||
540 !test_bit(ATM_VF_READY
, &vcc
->flags
))
543 skb
= skb_recv_datagram(sk
, flags
, &error
);
550 msg
->msg_flags
|= MSG_TRUNC
;
553 error
= skb_copy_datagram_msg(skb
, 0, msg
, copied
);
556 sock_recv_cmsgs(msg
, sk
, skb
);
558 if (!(flags
& MSG_PEEK
)) {
559 pr_debug("%d -= %d\n", atomic_read(&sk
->sk_rmem_alloc
),
561 atm_return(vcc
, skb
->truesize
);
564 skb_free_datagram(sk
, skb
);
568 int vcc_sendmsg(struct socket
*sock
, struct msghdr
*m
, size_t size
)
570 struct sock
*sk
= sock
->sk
;
577 if (sock
->state
!= SS_CONNECTED
) {
586 if (test_bit(ATM_VF_RELEASED
, &vcc
->flags
) ||
587 test_bit(ATM_VF_CLOSE
, &vcc
->flags
) ||
588 !test_bit(ATM_VF_READY
, &vcc
->flags
)) {
590 send_sig(SIGPIPE
, current
, 0);
597 if (size
> vcc
->qos
.txtp
.max_sdu
) {
602 eff
= (size
+3) & ~3; /* align to word boundary */
603 prepare_to_wait(sk_sleep(sk
), &wait
, TASK_INTERRUPTIBLE
);
605 while (!vcc_tx_ready(vcc
, eff
)) {
606 if (m
->msg_flags
& MSG_DONTWAIT
) {
611 if (signal_pending(current
)) {
612 error
= -ERESTARTSYS
;
615 if (test_bit(ATM_VF_RELEASED
, &vcc
->flags
) ||
616 test_bit(ATM_VF_CLOSE
, &vcc
->flags
) ||
617 !test_bit(ATM_VF_READY
, &vcc
->flags
)) {
619 send_sig(SIGPIPE
, current
, 0);
622 prepare_to_wait(sk_sleep(sk
), &wait
, TASK_INTERRUPTIBLE
);
624 finish_wait(sk_sleep(sk
), &wait
);
628 skb
= alloc_skb(eff
, GFP_KERNEL
);
633 pr_debug("%d += %d\n", sk_wmem_alloc_get(sk
), skb
->truesize
);
634 atm_account_tx(vcc
, skb
);
636 skb
->dev
= NULL
; /* for paths shared with net_device interfaces */
637 if (!copy_from_iter_full(skb_put(skb
, size
), size
, &m
->msg_iter
)) {
643 memset(skb
->data
+ size
, 0, eff
-size
);
644 error
= vcc
->dev
->ops
->send(vcc
, skb
);
645 error
= error
? error
: size
;
651 __poll_t
vcc_poll(struct file
*file
, struct socket
*sock
, poll_table
*wait
)
653 struct sock
*sk
= sock
->sk
;
657 sock_poll_wait(file
, sock
, wait
);
662 /* exceptional events */
666 if (test_bit(ATM_VF_RELEASED
, &vcc
->flags
) ||
667 test_bit(ATM_VF_CLOSE
, &vcc
->flags
))
671 if (!skb_queue_empty_lockless(&sk
->sk_receive_queue
))
672 mask
|= EPOLLIN
| EPOLLRDNORM
;
675 if (sock
->state
== SS_CONNECTING
&&
676 test_bit(ATM_VF_WAITING
, &vcc
->flags
))
679 if (vcc
->qos
.txtp
.traffic_class
!= ATM_NONE
&&
681 mask
|= EPOLLOUT
| EPOLLWRNORM
| EPOLLWRBAND
;
686 static int atm_change_qos(struct atm_vcc
*vcc
, struct atm_qos
*qos
)
691 * Don't let the QoS change the already connected AAL type nor the
694 if (qos
->aal
!= vcc
->qos
.aal
||
695 qos
->rxtp
.traffic_class
!= vcc
->qos
.rxtp
.traffic_class
||
696 qos
->txtp
.traffic_class
!= vcc
->qos
.txtp
.traffic_class
)
698 error
= adjust_tp(&qos
->txtp
, qos
->aal
);
700 error
= adjust_tp(&qos
->rxtp
, qos
->aal
);
703 if (!vcc
->dev
->ops
->change_qos
)
705 if (sk_atm(vcc
)->sk_family
== AF_ATMPVC
)
706 return vcc
->dev
->ops
->change_qos(vcc
, qos
, ATM_MF_SET
);
707 return svc_change_qos(vcc
, qos
);
710 static int check_tp(const struct atm_trafprm
*tp
)
712 /* @@@ Should be merged with adjust_tp */
713 if (!tp
->traffic_class
|| tp
->traffic_class
== ATM_ANYCLASS
)
715 if (tp
->traffic_class
!= ATM_UBR
&& !tp
->min_pcr
&& !tp
->pcr
&&
718 if (tp
->min_pcr
== ATM_MAX_PCR
)
720 if (tp
->min_pcr
&& tp
->max_pcr
&& tp
->max_pcr
!= ATM_MAX_PCR
&&
721 tp
->min_pcr
> tp
->max_pcr
)
724 * We allow pcr to be outside [min_pcr,max_pcr], because later
725 * adjustment may still push it in the valid range.
730 static int check_qos(const struct atm_qos
*qos
)
734 if (!qos
->txtp
.traffic_class
&& !qos
->rxtp
.traffic_class
)
736 if (qos
->txtp
.traffic_class
!= qos
->rxtp
.traffic_class
&&
737 qos
->txtp
.traffic_class
&& qos
->rxtp
.traffic_class
&&
738 qos
->txtp
.traffic_class
!= ATM_ANYCLASS
&&
739 qos
->rxtp
.traffic_class
!= ATM_ANYCLASS
)
741 error
= check_tp(&qos
->txtp
);
744 return check_tp(&qos
->rxtp
);
747 int vcc_setsockopt(struct socket
*sock
, int level
, int optname
,
748 sockptr_t optval
, unsigned int optlen
)
754 if (__SO_LEVEL_MATCH(optname
, level
) && optlen
!= __SO_SIZE(optname
))
763 if (copy_from_sockptr(&qos
, optval
, sizeof(qos
)))
765 error
= check_qos(&qos
);
768 if (sock
->state
== SS_CONNECTED
)
769 return atm_change_qos(vcc
, &qos
);
770 if (sock
->state
!= SS_UNCONNECTED
)
773 set_bit(ATM_VF_HASQOS
, &vcc
->flags
);
777 if (copy_from_sockptr(&value
, optval
, sizeof(value
)))
780 vcc
->atm_options
|= ATM_ATMOPT_CLP
;
782 vcc
->atm_options
&= ~ATM_ATMOPT_CLP
;
789 int vcc_getsockopt(struct socket
*sock
, int level
, int optname
,
790 char __user
*optval
, int __user
*optlen
)
795 if (get_user(len
, optlen
))
797 if (__SO_LEVEL_MATCH(optname
, level
) && len
!= __SO_SIZE(optname
))
803 if (!test_bit(ATM_VF_HASQOS
, &vcc
->flags
))
805 return copy_to_user(optval
, &vcc
->qos
, sizeof(vcc
->qos
))
808 return put_user(vcc
->atm_options
& ATM_ATMOPT_CLP
? 1 : 0,
809 (unsigned long __user
*)optval
) ? -EFAULT
: 0;
812 struct sockaddr_atmpvc pvc
;
814 if (!vcc
->dev
|| !test_bit(ATM_VF_ADDR
, &vcc
->flags
))
816 memset(&pvc
, 0, sizeof(pvc
));
817 pvc
.sap_family
= AF_ATMPVC
;
818 pvc
.sap_addr
.itf
= vcc
->dev
->number
;
819 pvc
.sap_addr
.vpi
= vcc
->vpi
;
820 pvc
.sap_addr
.vci
= vcc
->vci
;
821 return copy_to_user(optval
, &pvc
, sizeof(pvc
)) ? -EFAULT
: 0;
828 int register_atmdevice_notifier(struct notifier_block
*nb
)
830 return atomic_notifier_chain_register(&atm_dev_notify_chain
, nb
);
832 EXPORT_SYMBOL_GPL(register_atmdevice_notifier
);
834 void unregister_atmdevice_notifier(struct notifier_block
*nb
)
836 atomic_notifier_chain_unregister(&atm_dev_notify_chain
, nb
);
838 EXPORT_SYMBOL_GPL(unregister_atmdevice_notifier
);
840 static int __init
atm_init(void)
844 error
= proto_register(&vcc_proto
, 0);
847 error
= atmpvc_init();
849 pr_err("atmpvc_init() failed with %d\n", error
);
850 goto out_unregister_vcc_proto
;
852 error
= atmsvc_init();
854 pr_err("atmsvc_init() failed with %d\n", error
);
855 goto out_atmpvc_exit
;
857 error
= atm_proc_init();
859 pr_err("atm_proc_init() failed with %d\n", error
);
860 goto out_atmsvc_exit
;
862 error
= atm_sysfs_init();
864 pr_err("atm_sysfs_init() failed with %d\n", error
);
865 goto out_atmproc_exit
;
875 out_unregister_vcc_proto
:
876 proto_unregister(&vcc_proto
);
880 static void __exit
atm_exit(void)
886 proto_unregister(&vcc_proto
);
889 subsys_initcall(atm_init
);
891 module_exit(atm_exit
);
893 MODULE_DESCRIPTION("Asynchronous Transfer Mode (ATM) networking core");
894 MODULE_LICENSE("GPL");
895 MODULE_ALIAS_NETPROTO(PF_ATMPVC
);
896 MODULE_ALIAS_NETPROTO(PF_ATMSVC
);