From owner-svn-src-all@FreeBSD.ORG Sun Jun 6 20:34:18 2010 Return-Path: Delivered-To: svn-src-all@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id 39028106566C; Sun, 6 Jun 2010 20:34:18 +0000 (UTC) (envelope-from rrs@FreeBSD.org) Received: from svn.freebsd.org (unknown [IPv6:2001:4f8:fff6::2c]) by mx1.freebsd.org (Postfix) with ESMTP id 277698FC17; Sun, 6 Jun 2010 20:34:18 +0000 (UTC) Received: from svn.freebsd.org (localhost [127.0.0.1]) by svn.freebsd.org (8.14.3/8.14.3) with ESMTP id o56KYIAi047492; Sun, 6 Jun 2010 20:34:18 GMT (envelope-from rrs@svn.freebsd.org) Received: (from rrs@localhost) by svn.freebsd.org (8.14.3/8.14.3/Submit) id o56KYHoE047487; Sun, 6 Jun 2010 20:34:17 GMT (envelope-from rrs@svn.freebsd.org) Message-Id: <201006062034.o56KYHoE047487@svn.freebsd.org> From: Randall Stewart Date: Sun, 6 Jun 2010 20:34:17 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org X-SVN-Group: head MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Cc: Subject: svn commit: r208879 - head/sys/netinet X-BeenThere: svn-src-all@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: "SVN commit messages for the entire src tree \(except for " user" and " projects" \)" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Sun, 06 Jun 2010 20:34:18 -0000 Author: rrs Date: Sun Jun 6 20:34:17 2010 New Revision: 208879 URL: http://svn.freebsd.org/changeset/base/208879 Log: 1) Optimize the cleanup and don't always depend on the timer. This is done by considering the locks we will destroy and if they are contended we consider it the same as a reference count being up. Fixing this appears to cleanup another crash that was appearing with all the timers where the socket buf lock got corrupted. 2) Fix the sysctl code to take a lot more care when looking at INP's that are in the GONE or ALLGONE state. MFC after: 1 week Modified: head/sys/netinet/sctp_constants.h head/sys/netinet/sctp_lock_bsd.h head/sys/netinet/sctp_pcb.c head/sys/netinet/sctp_sysctl.c Modified: head/sys/netinet/sctp_constants.h ============================================================================== --- head/sys/netinet/sctp_constants.h Sun Jun 6 19:24:32 2010 (r208878) +++ head/sys/netinet/sctp_constants.h Sun Jun 6 20:34:17 2010 (r208879) @@ -894,7 +894,7 @@ __FBSDID("$FreeBSD$"); /* third argument */ #define SCTP_CALLED_DIRECTLY_NOCMPSET 0 #define SCTP_CALLED_AFTER_CMPSET_OFCLOSE 1 -#define SCTP_CALLED_FROM_INPKILL_TIMER 2 +#define SCTP_CALLED_FROM_INPKILL_TIMER 2 /* second argument */ #define SCTP_FREE_SHOULD_USE_ABORT 1 #define SCTP_FREE_SHOULD_USE_GRACEFUL_CLOSE 0 Modified: head/sys/netinet/sctp_lock_bsd.h ============================================================================== --- head/sys/netinet/sctp_lock_bsd.h Sun Jun 6 19:24:32 2010 (r208878) +++ head/sys/netinet/sctp_lock_bsd.h Sun Jun 6 20:34:17 2010 (r208879) @@ -185,6 +185,13 @@ extern int sctp_logoff_stuff; #define SCTP_INP_LOCK_DESTROY(_inp) \ mtx_destroy(&(_inp)->inp_mtx) +#define SCTP_INP_LOCK_CONTENDED(_inp) ((_inp)->inp_mtx.mtx_lock & MTX_CONTESTED) + +#define SCTP_INP_READ_CONTENDED(_inp) ((_inp)->inp_rdata_mtx.mtx_lock & MTX_CONTESTED) + +#define SCTP_ASOC_CREATE_LOCK_CONTENDED(_inp) ((_inp)->inp_create_mtx.mtx_lock & MTX_CONTESTED) + + #define SCTP_ASOC_CREATE_LOCK_DESTROY(_inp) \ mtx_destroy(&(_inp)->inp_create_mtx) Modified: head/sys/netinet/sctp_pcb.c ============================================================================== --- head/sys/netinet/sctp_pcb.c Sun Jun 6 19:24:32 2010 (r208878) +++ head/sys/netinet/sctp_pcb.c Sun Jun 6 20:34:17 2010 (r208879) @@ -3096,7 +3096,7 @@ sctp_inpcb_free(struct sctp_inpcb *inp, struct sctp_laddr *laddr, *nladdr; struct inpcb *ip_pcb; struct socket *so; - + int being_refed = 0; struct sctp_queued_to_read *sq; @@ -3423,9 +3423,16 @@ sctp_inpcb_free(struct sctp_inpcb *inp, #endif return; } + if (SCTP_INP_LOCK_CONTENDED(inp)) + being_refed++; + if (SCTP_INP_READ_CONTENDED(inp)) + being_refed++; + if (SCTP_ASOC_CREATE_LOCK_CONTENDED(inp)) + being_refed++; + if ((inp->refcount) || - (inp->sctp_flags & SCTP_PCB_FLAGS_CLOSE_IP) || - (from != SCTP_CALLED_FROM_INPKILL_TIMER)) { + (being_refed) || + (inp->sctp_flags & SCTP_PCB_FLAGS_CLOSE_IP)) { (void)SCTP_OS_TIMER_STOP(&inp->sctp_ep.signature_change.timer); sctp_timer_start(SCTP_TIMER_TYPE_INPKILL, inp, NULL, NULL); SCTP_INP_WUNLOCK(inp); Modified: head/sys/netinet/sctp_sysctl.c ============================================================================== --- head/sys/netinet/sctp_sysctl.c Sun Jun 6 19:24:32 2010 (r208878) +++ head/sys/netinet/sctp_sysctl.c Sun Jun 6 20:34:17 2010 (r208879) @@ -331,6 +331,7 @@ sctp_assoclist(SYSCTL_HANDLER_ARGS) struct xsctp_inpcb xinpcb; struct xsctp_tcb xstcb; struct xsctp_raddr xraddr; + struct socket *so; number_of_endpoints = 0; number_of_local_addresses = 0; @@ -369,6 +370,10 @@ sctp_assoclist(SYSCTL_HANDLER_ARGS) } LIST_FOREACH(inp, &SCTP_BASE_INFO(listhead), sctp_list) { SCTP_INP_RLOCK(inp); + if (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) { + /* if its allgone it is being freed - skip it */ + goto skip; + } xinpcb.last = 0; xinpcb.local_port = ntohs(inp->sctp_lport); xinpcb.flags = inp->sctp_flags; @@ -377,13 +382,14 @@ sctp_assoclist(SYSCTL_HANDLER_ARGS) xinpcb.total_recvs = inp->total_recvs; xinpcb.total_nospaces = inp->total_nospaces; xinpcb.fragmentation_point = inp->sctp_frag_point; - if ((inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) || + so = inp->sctp_socket; + if ((so == NULL) || (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE)) { xinpcb.qlen = 0; xinpcb.maxqlen = 0; } else { - xinpcb.qlen = inp->sctp_socket->so_qlen; - xinpcb.maxqlen = inp->sctp_socket->so_qlimit; + xinpcb.qlen = so->so_qlen; + xinpcb.maxqlen = so->so_qlimit; } SCTP_INP_INCR_REF(inp); SCTP_INP_RUNLOCK(inp); @@ -501,6 +507,7 @@ sctp_assoclist(SYSCTL_HANDLER_ARGS) if (error) { return error; } +skip: SCTP_INP_INFO_RLOCK(); } SCTP_INP_INFO_RUNLOCK();