If there is socket error (the peer crashes, or the
cable is pulled whatever) while the session is being
started (i.e. inside session_start), we may get
coredump, because the iostate has been deleted by the
thread handling socket I/O, but in session_start() we
are still referencing it.
This diff may be the right fix:
@@ -2054,10 +2110,20 @@ session_start(WRAPPER* wrap)
if (wrap->conn.role == 'I')
bp_wait_for_greeting(&wrap->conn);
/* force seq after greeting to go out */
- fiostate_unblock_write(wrap->iostate);
- if (wrap->conn.status == INST_STATUS_EXIT) {
- session_shutdown(wrap);
- }
+ /*
+ * The iostate may have been deleted while we are
waiting for greetings.
+ */
+ SEM_WAIT(&wrap->lock);
+ if (wrap->iostate)
+ fiostate_unblock_write(wrap->iostate);
+ else
+ ret = 1;
+ SEM_POST(&wrap->lock);
+
+ /*
+ * Return error code and the caller should cleanup
the session.
+ */
+ return ret;
}