All fatal errors will be passed to the user as an error return even when the socket is not connected. This includes asynchronous errors received from the network. You may get an error for an earlier packet that was sent on the same socket. This behaviour differs from many other BSD socket implementations which dont pass any errors unless the socket is connected. Linuxs behaviour is mandated by RFC1122.
For compatibility with legacy code it is possible to set the SO_BSDCOMPAT SOL_SOCKET option to receive remote errors only when the socket has been connected (except for EPROTO and EMSGSIZE). It is better to fix the code to handle errors properly than to enable this option. Locally generated errors are always passed.
When the IP_RECVERR option is enabled all errors are stored in the socket error queue and can be received by recvmsg(2) with the MSG_ERRQUEUE flag set.
These ioctls can be accessed using ioctl(2). The correct syntax is:
error" = ioctl("tcp_socket", "ioctl_type", &"value");"