1 // vim: noet sw=4 ts=4:
3 ==================================================================================
4 Copyright (c) 2020 Nokia
5 Copyright (c) 2020 AT&T Intellectual Property.
7 Licensed under the Apache License, Version 2.0 (the "License");
8 you may not use this file except in compliance with the License.
9 You may obtain a copy of the License at
11 http://www.apache.org/licenses/LICENSE-2.0
13 Unless required by applicable law or agreed to in writing, software
14 distributed under the License is distributed on an "AS IS" BASIS,
15 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 See the License for the specific language governing permissions and
17 limitations under the License.
18 ==================================================================================
22 **************************************************************************
24 * Abstract: Manage the transport provider block information relating to
25 * the need to terminate the session. The block is left in the
26 * list; it is unsafe to clean the lsit up outside of the SIwait
27 * thread. When safe, the SIrm_tpb() function can be called to
28 * do the rest of the work that was originally done by SIterm.
30 * Date: 18 January 1995
31 * Author: E. Scott Daniels
33 **************************************************************************
35 #include "sisetup.h" // get the setup stuff
36 #include "sitransport.h"
40 Abort the connection in such a way that there is no resulting time-wait state.
41 This should be used cautiously but is needed for situations like when the Linux
42 connect() system call manages to connect us to ourselves through the even number
45 This needs a real file desc as there may not yet be a transport block when
46 the connection may need to be aborted. For this reason, the function name is
47 lower case indicating that user programmes are discouraged from using this
50 extern void siabort_conn( int fd ) {
51 struct linger opt_val; // value passed as option to set call
53 opt_val.l_onoff = 1; // MUST set linger on with a zero len timeout
56 setsockopt( fd, SOL_SOCKET, SO_LINGER, &opt_val, sizeof( opt_val ) ); // disable linger to prevent time-wait
57 CLOSE( fd ); // close will now abort and not result in time-wait (do NOT use shutdown() first!)
61 Close the FD and mark the transport block as unusable/closed.
62 Removal of the block from the list is safe only from the siwait
63 thread. If the abort flag is set in the transport block, then the
64 connection is aborted (reset).
66 extern void SIterm( struct ginfo_blk* gptr, struct tp_blk *tpptr ) {
69 if( tpptr->fd >= 0 ) {
70 if( tpptr->flags & TPF_ABORT ) {
71 siabort_conn( tpptr->fd );
76 if( tpptr->fd < MAX_FDS ) {
77 gptr->tp_map[tpptr->fd] = NULL; // drop reference
81 tpptr->fd = -1; // prevent future sends etc.
82 tpptr->flags |= TPF_DELETE; // signal block deletion needed when safe
87 It is safe to remove the block from the list; if it was in the list
90 extern void SIrm_tpb( struct ginfo_blk *gptr, struct tp_blk *tpptr ) {
93 if( tpptr->prev != NULL || tpptr->next != NULL ) { // in the list
94 if( tpptr->prev != NULL ) { // remove from the list
95 tpptr->prev->next = tpptr->next; // point previous at the next
97 gptr->tplist = tpptr->next; // this was head, make next new head
100 if( tpptr->next != NULL ) {
101 tpptr->next->prev = tpptr->prev; // point next one back behind this one
105 free( tpptr->addr ); // release the address bufers
106 free( tpptr->paddr );
107 free( tpptr ); // and release the block