Print this page
OS-4865 lxbrand async socket errors catch programs off guard
Reviewed by: Jerry Jelinek <jerry.jelinek@joyent.com>
OS-4213 lxbrand should be able to set TCP_DEFER_ACCEPT after other socket operations

*** 295,313 **** #define SS_RCVATMARK 0x00001000 /* at mark on input */ #define SS_OOBPEND 0x00002000 /* OOB pending or present - poll */ #define SS_HAVEOOBDATA 0x00004000 /* OOB data present */ #define SS_HADOOBDATA 0x00008000 /* OOB data consumed */ - #define SS_CLOSING 0x00010000 /* in process of closing */ #define SS_FIL_DEFER 0x00020000 /* filter deferred notification */ #define SS_FILOP_OK 0x00040000 /* socket can attach filters */ #define SS_FIL_RCV_FLOWCTRL 0x00080000 /* filter asserted rcv flow ctrl */ #define SS_FIL_SND_FLOWCTRL 0x00100000 /* filter asserted snd flow ctrl */ #define SS_FIL_STOP 0x00200000 /* no more filter actions */ - #define SS_SODIRECT 0x00400000 /* transport supports sodirect */ #define SS_SENTLASTREADSIG 0x01000000 /* last rx signal has been sent */ #define SS_SENTLASTWRITESIG 0x02000000 /* last tx signal has been sent */ #define SS_FALLBACK_DRAIN 0x20000000 /* data was/is being drained */ --- 295,314 ---- #define SS_RCVATMARK 0x00001000 /* at mark on input */ #define SS_OOBPEND 0x00002000 /* OOB pending or present - poll */ #define SS_HAVEOOBDATA 0x00004000 /* OOB data present */ #define SS_HADOOBDATA 0x00008000 /* OOB data consumed */ + #define SS_CLOSING 0x00010000 /* in process of closing */ #define SS_FIL_DEFER 0x00020000 /* filter deferred notification */ #define SS_FILOP_OK 0x00040000 /* socket can attach filters */ #define SS_FIL_RCV_FLOWCTRL 0x00080000 /* filter asserted rcv flow ctrl */ + #define SS_FIL_SND_FLOWCTRL 0x00100000 /* filter asserted snd flow ctrl */ #define SS_FIL_STOP 0x00200000 /* no more filter actions */ #define SS_SODIRECT 0x00400000 /* transport supports sodirect */ + #define SS_FILOP_UNSF 0x00800000 /* block attaching unsafe filters */ #define SS_SENTLASTREADSIG 0x01000000 /* last rx signal has been sent */ #define SS_SENTLASTWRITESIG 0x02000000 /* last tx signal has been sent */ #define SS_FALLBACK_DRAIN 0x20000000 /* data was/is being drained */
*** 319,329 **** #define SS_CANTREBIND (SS_ISCONNECTED|SS_ISCONNECTING|SS_ISDISCONNECTING|\ SS_CANTSENDMORE|SS_CANTRCVMORE|SS_ACCEPTCONN) /* * Sockets that can fall back to TPI must ensure that fall back is not ! * initiated while a thread is using a socket. */ #define SO_BLOCK_FALLBACK(so, fn) \ ASSERT(MUTEX_NOT_HELD(&(so)->so_lock)); \ rw_enter(&(so)->so_fallback_rwlock, RW_READER); \ if ((so)->so_state & (SS_FALLBACK_COMP|SS_FILOP_OK)) { \ --- 320,331 ---- #define SS_CANTREBIND (SS_ISCONNECTED|SS_ISCONNECTING|SS_ISDISCONNECTING|\ SS_CANTSENDMORE|SS_CANTRCVMORE|SS_ACCEPTCONN) /* * Sockets that can fall back to TPI must ensure that fall back is not ! * initiated while a thread is using a socket. Otherwise this disables all ! * future filter attachment. */ #define SO_BLOCK_FALLBACK(so, fn) \ ASSERT(MUTEX_NOT_HELD(&(so)->so_lock)); \ rw_enter(&(so)->so_fallback_rwlock, RW_READER); \ if ((so)->so_state & (SS_FALLBACK_COMP|SS_FILOP_OK)) { \
*** 335,344 **** --- 337,364 ---- (so)->so_state &= ~SS_FILOP_OK; \ mutex_exit(&(so)->so_lock); \ } \ } + /* + * Sockets that can fall back to TPI must ensure that fall back is not + * initiated while a thread is using a socket. Otherwise this disables all + * future unsafe filter attachment. Safe filters can still attach after + * we execute the function in which this macro is used. + */ + #define SO_BLOCK_FALLBACK_SAFE(so, fn) \ + ASSERT(MUTEX_NOT_HELD(&(so)->so_lock)); \ + rw_enter(&(so)->so_fallback_rwlock, RW_READER); \ + if ((so)->so_state & SS_FALLBACK_COMP) { \ + rw_exit(&(so)->so_fallback_rwlock); \ + return (fn); \ + } else if (((so)->so_state & SS_FILOP_UNSF) == 0) { \ + mutex_enter(&(so)->so_lock); \ + (so)->so_state |= SS_FILOP_UNSF; \ + mutex_exit(&(so)->so_lock); \ + } + #define SO_UNBLOCK_FALLBACK(so) { \ rw_exit(&(so)->so_fallback_rwlock); \ } #define SO_SND_FLOWCTRLD(so) \
*** 366,375 **** --- 386,396 ---- #define SM_KERNEL 0x200 /* kernel socket */ /* The modes below are only for non-streams sockets */ #define SM_ACCEPTSUPP 0x400 /* can handle accept() */ #define SM_SENDFILESUPP 0x800 /* Private: proto supp sendfile */ + #define SM_DEFERERR 0x1000 /* Private: defer so_error delivery */ /* * Socket versions. Used by the socket library when calling _so_socket(). */ #define SOV_STREAM 0 /* Not a socket - just a stream */