if (IsDefunct(client_p))
return;
- /*
- * Read some data. We *used to* do anti-flood protection here, but
- * I personally think it makes the code too hairy to make sane.
- * -- adrian
- */
- if (fd->ssl)
+ do
{
- ERR_clear_error();
- length = SSL_read(fd->ssl, readBuf, READBUF_SIZE);
+ /*
+ * Read some data. We *used to* do anti-flood protection here, but
+ * I personally think it makes the code too hairy to make sane.
+ * -- adrian
+ */
+ if (fd->ssl)
+ {
+ ERR_clear_error();
+ length = SSL_read(fd->ssl, readBuf, READBUF_SIZE);
+
+ if (!IsServer(client_p) && fd->renegotiations > 1)
+ {
+ exit_client(client_p, &me, "SSL renegotiation not allowed");
+ return;
+ }
- if (!IsServer(client_p) && fd->renegotiations > 1)
+ /* translate openssl error codes, sigh */
+ if (length < 0)
+ switch (SSL_get_error(fd->ssl, length))
+ {
+ case SSL_ERROR_WANT_WRITE:
+ comm_setselect(fd, COMM_SELECT_WRITE, (PF *) sendq_unblocked, client_p);
+ return;
+ case SSL_ERROR_WANT_READ:
+ errno = EWOULDBLOCK;
+ case SSL_ERROR_SYSCALL:
+ break;
+ case SSL_ERROR_SSL:
+ if (errno == EAGAIN)
+ break;
+ default:
+ length = errno = 0;
+ }
+ }
+ else
{
- exit_client(client_p, &me, "SSL renegotiation not allowed");
- return;
+ length = recv(fd->fd, readBuf, READBUF_SIZE, 0);
}
- /* translate openssl error codes, sigh */
- if (length < 0)
- switch (SSL_get_error(fd->ssl, length))
+ if (length <= 0)
+ {
+ if (length < 0 && ignoreErrno(errno))
{
- case SSL_ERROR_WANT_WRITE:
- comm_setselect(fd, COMM_SELECT_WRITE, (PF *) sendq_unblocked, client_p);
- return;
- case SSL_ERROR_WANT_READ:
- errno = EWOULDBLOCK;
- case SSL_ERROR_SYSCALL:
- break;
- case SSL_ERROR_SSL:
- if (errno == EAGAIN)
- break;
- default:
- length = errno = 0;
+ comm_setselect(fd, COMM_SELECT_READ, read_packet, client_p);
+ return;
}
- }
- else
- {
- length = recv(fd->fd, readBuf, READBUF_SIZE, 0);
- }
- if (length <= 0)
- {
- if (length < 0 && ignoreErrno(errno))
- {
- comm_setselect(fd, COMM_SELECT_READ, read_packet, client_p);
+ dead_link_on_read(client_p, length);
return;
}
- dead_link_on_read(client_p, length);
- return;
- }
+ dbuf_put(&client_p->localClient->buf_recvq, readBuf, length);
- dbuf_put(&client_p->localClient->buf_recvq, readBuf, length);
+ if (client_p->localClient->lasttime < CurrentTime)
+ client_p->localClient->lasttime = CurrentTime;
+ if (client_p->localClient->lasttime > client_p->localClient->since)
+ client_p->localClient->since = CurrentTime;
+ ClearPingSent(client_p);
- if (client_p->localClient->lasttime < CurrentTime)
- client_p->localClient->lasttime = CurrentTime;
- if (client_p->localClient->lasttime > client_p->localClient->since)
- client_p->localClient->since = CurrentTime;
- ClearPingSent(client_p);
-
- /* Attempt to parse what we have */
- parse_client_queued(client_p);
+ /* Attempt to parse what we have */
+ parse_client_queued(client_p);
- if (IsDefunct(client_p))
- return;
+ if (IsDefunct(client_p))
+ return;
- if (IsServer(client_p) && HasSFlag(client_p, SERVER_FLAGS_MIGRATING_BLOCK_READ))
- return;
+ if (IsServer(client_p) && HasSFlag(client_p, SERVER_FLAGS_MIGRATING_BLOCK_READ))
+ return;
- /* Check to make sure we're not flooding */
- if (!(IsServer(client_p) || IsHandshake(client_p) || IsConnecting(client_p))
- && (dbuf_length(&client_p->localClient->buf_recvq) >
- get_recvq(&client_p->localClient->confs)))
- {
- exit_client(client_p, client_p, "Excess Flood");
- return;
+ /* Check to make sure we're not flooding */
+ if (!(IsServer(client_p) || IsHandshake(client_p) || IsConnecting(client_p))
+ && (dbuf_length(&client_p->localClient->buf_recvq) >
+ get_recvq(&client_p->localClient->confs)))
+ {
+ exit_client(client_p, client_p, "Excess Flood");
+ return;
+ }
}
+ while (length == sizeof(readBuf) || fd->ssl != NULL);
/* If we get here, we need to register for another COMM_SELECT_READ */
comm_setselect(fd, COMM_SELECT_READ, read_packet, client_p);