- if (head != NULL) {
- if (so->so_state & SS_INCOMP) {
- TAILQ_REMOVE(&head->so_incomp, so, so_list);
- head->so_incqlen--;
- } else if (so->so_state & SS_COMP) {
- TAILQ_REMOVE(&head->so_comp, so, so_list);
- } else {
- panic("sofree: not queued");
- }
+ }
+ if (head != NULL) {
+ if (so->so_state & SS_INCOMP) {
+ TAILQ_REMOVE(&head->so_incomp, so, so_list);
+ head->so_incqlen--;
+ } else if (so->so_state & SS_COMP) {
+ /*
+ * We must not decommission a socket that's
+ * on the accept(2) queue. If we do, then
+ * accept(2) may hang after select(2) indicated
+ * that the listening socket was ready.
+ */
+ selthreadclear(&so->so_snd.sb_sel);
+ selthreadclear(&so->so_rcv.sb_sel);
+ return;
+ } else {
+ panic("sofree: not queued");
+ }