Lines Matching +full:wait +full:- +full:state

1 // SPDX-License-Identifier: GPL-2.0
2 /* net/atm/svc.c - ATM SVC sockets */
4 /* Written 1995-2000 by Werner Almesberger, EPFL LRC/ICA */
13 #include <linux/wait.h>
53 DEFINE_WAIT(wait); in svc_disconnect()
58 if (test_bit(ATM_VF_REGIS, &vcc->flags)) { in svc_disconnect()
61 prepare_to_wait(sk_sleep(sk), &wait, TASK_UNINTERRUPTIBLE); in svc_disconnect()
62 if (test_bit(ATM_VF_RELEASED, &vcc->flags) || !sigd) in svc_disconnect()
66 finish_wait(sk_sleep(sk), &wait); in svc_disconnect()
68 /* beware - socket is still in use by atmsigd until the last in svc_disconnect()
70 while ((skb = skb_dequeue(&sk->sk_receive_queue)) != NULL) { in svc_disconnect()
71 atm_return(vcc, skb->truesize); in svc_disconnect()
73 sigd_enq2(NULL, as_reject, vcc, NULL, NULL, &vcc->qos, 0); in svc_disconnect()
76 clear_bit(ATM_VF_REGIS, &vcc->flags); in svc_disconnect()
82 struct sock *sk = sock->sk; in svc_release()
88 clear_bit(ATM_VF_READY, &vcc->flags); in svc_release()
91 * so we must not free it (thereby subjecting it to re-use) in svc_release()
103 DEFINE_WAIT(wait); in svc_bind()
104 struct sock *sk = sock->sk; in svc_bind()
110 return -EINVAL; in svc_bind()
112 if (sock->state == SS_CONNECTED) { in svc_bind()
113 error = -EISCONN; in svc_bind()
116 if (sock->state != SS_UNCONNECTED) { in svc_bind()
117 error = -EINVAL; in svc_bind()
122 if (addr->sas_family != AF_ATMSVC) { in svc_bind()
123 error = -EAFNOSUPPORT; in svc_bind()
126 clear_bit(ATM_VF_BOUND, &vcc->flags); in svc_bind()
129 if (!test_bit(ATM_VF_HASQOS, &vcc->flags)) { in svc_bind()
130 error = -EBADFD; in svc_bind()
133 vcc->local = *addr; in svc_bind()
134 set_bit(ATM_VF_WAITING, &vcc->flags); in svc_bind()
135 sigd_enq(vcc, as_bind, NULL, NULL, &vcc->local); in svc_bind()
137 prepare_to_wait(sk_sleep(sk), &wait, TASK_UNINTERRUPTIBLE); in svc_bind()
138 if (!test_bit(ATM_VF_WAITING, &vcc->flags) || !sigd) in svc_bind()
142 finish_wait(sk_sleep(sk), &wait); in svc_bind()
143 clear_bit(ATM_VF_REGIS, &vcc->flags); /* doesn't count */ in svc_bind()
145 error = -EUNATCH; in svc_bind()
148 if (!sk->sk_err) in svc_bind()
149 set_bit(ATM_VF_BOUND, &vcc->flags); in svc_bind()
150 error = -sk->sk_err; in svc_bind()
159 DEFINE_WAIT(wait); in svc_connect()
160 struct sock *sk = sock->sk; in svc_connect()
168 error = -EINVAL; in svc_connect()
172 switch (sock->state) { in svc_connect()
174 error = -EINVAL; in svc_connect()
177 error = -EISCONN; in svc_connect()
180 if (test_bit(ATM_VF_WAITING, &vcc->flags)) { in svc_connect()
181 error = -EALREADY; in svc_connect()
184 sock->state = SS_UNCONNECTED; in svc_connect()
185 if (sk->sk_err) { in svc_connect()
186 error = -sk->sk_err; in svc_connect()
192 if (addr->sas_family != AF_ATMSVC) { in svc_connect()
193 error = -EAFNOSUPPORT; in svc_connect()
196 if (!test_bit(ATM_VF_HASQOS, &vcc->flags)) { in svc_connect()
197 error = -EBADFD; in svc_connect()
200 if (vcc->qos.txtp.traffic_class == ATM_ANYCLASS || in svc_connect()
201 vcc->qos.rxtp.traffic_class == ATM_ANYCLASS) { in svc_connect()
202 error = -EINVAL; in svc_connect()
205 if (!vcc->qos.txtp.traffic_class && in svc_connect()
206 !vcc->qos.rxtp.traffic_class) { in svc_connect()
207 error = -EINVAL; in svc_connect()
210 vcc->remote = *addr; in svc_connect()
211 set_bit(ATM_VF_WAITING, &vcc->flags); in svc_connect()
212 sigd_enq(vcc, as_connect, NULL, NULL, &vcc->remote); in svc_connect()
214 sock->state = SS_CONNECTING; in svc_connect()
215 error = -EINPROGRESS; in svc_connect()
219 prepare_to_wait(sk_sleep(sk), &wait, TASK_INTERRUPTIBLE); in svc_connect()
220 while (test_bit(ATM_VF_WAITING, &vcc->flags) && sigd) { in svc_connect()
223 prepare_to_wait(sk_sleep(sk), &wait, in svc_connect()
230 * Kernel ---close--> Demon in svc_connect()
231 * Kernel <--close--- Demon in svc_connect()
233 * Kernel ---close--> Demon in svc_connect()
234 * Kernel <--error--- Demon in svc_connect()
236 * Kernel ---close--> Demon in svc_connect()
237 * Kernel <--okay---- Demon in svc_connect()
238 * Kernel <--close--- Demon in svc_connect()
241 while (test_bit(ATM_VF_WAITING, &vcc->flags) && sigd) { in svc_connect()
242 prepare_to_wait(sk_sleep(sk), &wait, in svc_connect()
246 if (!sk->sk_err) in svc_connect()
247 while (!test_bit(ATM_VF_RELEASED, &vcc->flags) && in svc_connect()
249 prepare_to_wait(sk_sleep(sk), &wait, in svc_connect()
253 clear_bit(ATM_VF_REGIS, &vcc->flags); in svc_connect()
254 clear_bit(ATM_VF_RELEASED, &vcc->flags); in svc_connect()
255 clear_bit(ATM_VF_CLOSE, &vcc->flags); in svc_connect()
257 error = -EINTR; in svc_connect()
260 finish_wait(sk_sleep(sk), &wait); in svc_connect()
264 error = -EUNATCH; in svc_connect()
267 if (sk->sk_err) { in svc_connect()
268 error = -sk->sk_err; in svc_connect()
273 vcc->qos.txtp.max_pcr = SELECT_TOP_PCR(vcc->qos.txtp); in svc_connect()
274 vcc->qos.txtp.pcr = 0; in svc_connect()
275 vcc->qos.txtp.min_pcr = 0; in svc_connect()
277 error = vcc_connect(sock, vcc->itf, vcc->vpi, vcc->vci); in svc_connect()
279 sock->state = SS_CONNECTED; in svc_connect()
289 DEFINE_WAIT(wait); in svc_listen()
290 struct sock *sk = sock->sk; in svc_listen()
297 if (test_bit(ATM_VF_SESSION, &vcc->flags)) { in svc_listen()
298 error = -EINVAL; in svc_listen()
301 if (test_bit(ATM_VF_LISTEN, &vcc->flags)) { in svc_listen()
302 error = -EADDRINUSE; in svc_listen()
305 set_bit(ATM_VF_WAITING, &vcc->flags); in svc_listen()
306 sigd_enq(vcc, as_listen, NULL, NULL, &vcc->local); in svc_listen()
308 prepare_to_wait(sk_sleep(sk), &wait, TASK_UNINTERRUPTIBLE); in svc_listen()
309 if (!test_bit(ATM_VF_WAITING, &vcc->flags) || !sigd) in svc_listen()
313 finish_wait(sk_sleep(sk), &wait); in svc_listen()
315 error = -EUNATCH; in svc_listen()
318 set_bit(ATM_VF_LISTEN, &vcc->flags); in svc_listen()
320 sk->sk_max_ack_backlog = backlog > 0 ? backlog : ATM_BACKLOG_DEFAULT; in svc_listen()
321 error = -sk->sk_err; in svc_listen()
330 struct sock *sk = sock->sk; in svc_accept()
339 error = svc_create(sock_net(sk), newsock, 0, arg->kern); in svc_accept()
345 pr_debug("%p -> %p\n", old_vcc, new_vcc); in svc_accept()
347 DEFINE_WAIT(wait); in svc_accept()
349 prepare_to_wait(sk_sleep(sk), &wait, TASK_INTERRUPTIBLE); in svc_accept()
350 while (!(skb = skb_dequeue(&sk->sk_receive_queue)) && in svc_accept()
352 if (test_bit(ATM_VF_RELEASED, &old_vcc->flags)) in svc_accept()
354 if (test_bit(ATM_VF_CLOSE, &old_vcc->flags)) { in svc_accept()
355 error = -sk->sk_err; in svc_accept()
358 if (arg->flags & O_NONBLOCK) { in svc_accept()
359 error = -EAGAIN; in svc_accept()
366 error = -ERESTARTSYS; in svc_accept()
369 prepare_to_wait(sk_sleep(sk), &wait, in svc_accept()
372 finish_wait(sk_sleep(sk), &wait); in svc_accept()
376 error = -EUNATCH; in svc_accept()
379 msg = (struct atmsvc_msg *)skb->data; in svc_accept()
380 new_vcc->qos = msg->qos; in svc_accept()
381 set_bit(ATM_VF_HASQOS, &new_vcc->flags); in svc_accept()
382 new_vcc->remote = msg->svc; in svc_accept()
383 new_vcc->local = msg->local; in svc_accept()
384 new_vcc->sap = msg->sap; in svc_accept()
385 error = vcc_connect(newsock, msg->pvc.sap_addr.itf, in svc_accept()
386 msg->pvc.sap_addr.vpi, in svc_accept()
387 msg->pvc.sap_addr.vci); in svc_accept()
392 &old_vcc->qos, error); in svc_accept()
393 error = error == -EAGAIN ? -EBUSY : error; in svc_accept()
396 /* wait should be short, so we ignore the non-blocking flag */ in svc_accept()
397 set_bit(ATM_VF_WAITING, &new_vcc->flags); in svc_accept()
400 prepare_to_wait(sk_sleep(sk_atm(new_vcc)), &wait, in svc_accept()
402 if (!test_bit(ATM_VF_WAITING, &new_vcc->flags) || !sigd) in svc_accept()
408 finish_wait(sk_sleep(sk_atm(new_vcc)), &wait); in svc_accept()
410 error = -EUNATCH; in svc_accept()
413 if (!sk_atm(new_vcc)->sk_err) in svc_accept()
415 if (sk_atm(new_vcc)->sk_err != ERESTARTSYS) { in svc_accept()
416 error = -sk_atm(new_vcc)->sk_err; in svc_accept()
420 newsock->state = SS_CONNECTED; in svc_accept()
432 memcpy(addr, peer ? &ATM_SD(sock)->remote : &ATM_SD(sock)->local, in svc_getname()
440 DEFINE_WAIT(wait); in svc_change_qos()
442 set_bit(ATM_VF_WAITING, &vcc->flags); in svc_change_qos()
443 sigd_enq2(vcc, as_modify, NULL, NULL, &vcc->local, qos, 0); in svc_change_qos()
445 prepare_to_wait(sk_sleep(sk), &wait, TASK_UNINTERRUPTIBLE); in svc_change_qos()
446 if (!test_bit(ATM_VF_WAITING, &vcc->flags) || in svc_change_qos()
447 test_bit(ATM_VF_RELEASED, &vcc->flags) || !sigd) { in svc_change_qos()
452 finish_wait(sk_sleep(sk), &wait); in svc_change_qos()
454 return -EUNATCH; in svc_change_qos()
455 return -sk->sk_err; in svc_change_qos()
461 struct sock *sk = sock->sk; in svc_setsockopt()
469 error = -EINVAL; in svc_setsockopt()
472 if (copy_from_sockptr(&vcc->sap, optval, optlen)) { in svc_setsockopt()
473 error = -EFAULT; in svc_setsockopt()
476 set_bit(ATM_VF_HASSAP, &vcc->flags); in svc_setsockopt()
480 error = -EINVAL; in svc_setsockopt()
484 error = -EFAULT; in svc_setsockopt()
488 set_bit(ATM_VF_SESSION, &vcc->flags); in svc_setsockopt()
490 clear_bit(ATM_VF_SESSION, &vcc->flags); in svc_setsockopt()
492 error = -EINVAL; in svc_setsockopt()
506 struct sock *sk = sock->sk; in svc_getsockopt()
515 error = -EFAULT; in svc_getsockopt()
519 error = -EINVAL; in svc_getsockopt()
522 if (copy_to_user(optval, &ATM_SD(sock)->sap, sizeof(struct atm_sap))) { in svc_getsockopt()
523 error = -EFAULT; in svc_getsockopt()
534 DEFINE_WAIT(wait); in svc_addparty()
535 struct sock *sk = sock->sk; in svc_addparty()
540 set_bit(ATM_VF_WAITING, &vcc->flags); in svc_addparty()
544 error = -EINPROGRESS; in svc_addparty()
547 pr_debug("added wait queue\n"); in svc_addparty()
549 prepare_to_wait(sk_sleep(sk), &wait, TASK_INTERRUPTIBLE); in svc_addparty()
550 if (!test_bit(ATM_VF_WAITING, &vcc->flags) || !sigd) in svc_addparty()
554 finish_wait(sk_sleep(sk), &wait); in svc_addparty()
555 error = -xchg(&sk->sk_err_soft, 0); in svc_addparty()
563 DEFINE_WAIT(wait); in svc_dropparty()
564 struct sock *sk = sock->sk; in svc_dropparty()
569 set_bit(ATM_VF_WAITING, &vcc->flags); in svc_dropparty()
572 prepare_to_wait(sk_sleep(sk), &wait, TASK_INTERRUPTIBLE); in svc_dropparty()
573 if (!test_bit(ATM_VF_WAITING, &vcc->flags) || !sigd) in svc_dropparty()
577 finish_wait(sk_sleep(sk), &wait); in svc_dropparty()
579 error = -EUNATCH; in svc_dropparty()
582 error = -xchg(&sk->sk_err_soft, 0); in svc_dropparty()
596 if (!test_bit(ATM_VF_SESSION, &vcc->flags)) in svc_ioctl()
597 return -EINVAL; in svc_ioctl()
599 return -EFAULT; in svc_ioctl()
604 if (!test_bit(ATM_VF_SESSION, &vcc->flags)) in svc_ioctl()
605 return -EINVAL; in svc_ioctl()
607 return -EFAULT; in svc_ioctl()
666 return -EAFNOSUPPORT; in svc_create()
668 sock->ops = &svc_proto_ops; in svc_create()
672 ATM_SD(sock)->local.sas_family = AF_ATMSVC; in svc_create()
673 ATM_SD(sock)->remote.sas_family = AF_ATMSVC; in svc_create()