Если сокет помечен как не блокирующий, recv никогда не заблокирует. период.
Если с сокетом все в порядке, но данных для чтения нет, вы получите -1 в качестве возвращаемого значения, а для errno будет установлено значение EAGAIN.
Если есть ошибка (закрытый сокет и т. Д.), Вы все равно получите возвращаемое значение -1, но для errno будет установлено соответствующее значение.