MINOR: checks: adapt to the new buffer API

The code exclusively used ->i for data received and ->o for data sent. Now
it always uses b_data(), b_head() and b_tail() so that there is no more
distinction between ->i and ->o.
This commit is contained in:
Willy Tarreau 2018-06-18 11:11:07 +02:00
parent cd9e60db00
commit 876171e636

View File

@ -745,8 +745,8 @@ static void event_srv_chk_w(struct conn_stream *cs)
if (check->type == PR_O2_TCPCHK_CHK) if (check->type == PR_O2_TCPCHK_CHK)
goto out_unlock; goto out_unlock;
if (check->bo->o) { if (b_data(check->bo)) {
b_del(check->bo, conn->mux->snd_buf(cs, check->bo, check->bo->o, 0)); b_del(check->bo, conn->mux->snd_buf(cs, check->bo, b_data(check->bo), 0));
b_realign_if_empty(check->bo); b_realign_if_empty(check->bo);
if (conn->flags & CO_FL_ERROR || cs->flags & CS_FL_ERROR) { if (conn->flags & CO_FL_ERROR || cs->flags & CS_FL_ERROR) {
@ -754,7 +754,7 @@ static void event_srv_chk_w(struct conn_stream *cs)
__cs_stop_both(cs); __cs_stop_both(cs);
goto out_wakeup; goto out_wakeup;
} }
if (check->bo->o) if (b_data(check->bo))
goto out_unlock; goto out_unlock;
} }
@ -827,7 +827,7 @@ static void event_srv_chk_r(struct conn_stream *cs)
conn->mux->rcv_buf(cs, check->bi, check->bi->size, 0); conn->mux->rcv_buf(cs, check->bi, check->bi->size, 0);
if (conn->flags & (CO_FL_ERROR | CO_FL_SOCK_RD_SH) || cs->flags & CS_FL_ERROR) { if (conn->flags & (CO_FL_ERROR | CO_FL_SOCK_RD_SH) || cs->flags & CS_FL_ERROR) {
done = 1; done = 1;
if ((conn->flags & CO_FL_ERROR || cs->flags & CS_FL_ERROR) && !check->bi->i) { if ((conn->flags & CO_FL_ERROR || cs->flags & CS_FL_ERROR) && !b_data(check->bi)) {
/* Report network errors only if we got no other data. Otherwise /* Report network errors only if we got no other data. Otherwise
* we'll let the upper layers decide whether the response is OK * we'll let the upper layers decide whether the response is OK
* or not. It is very common that an RST sent by the server is * or not. It is very common that an RST sent by the server is
@ -840,35 +840,35 @@ static void event_srv_chk_r(struct conn_stream *cs)
/* Intermediate or complete response received. /* Intermediate or complete response received.
* Terminate string in check->bi->data buffer. * Terminate string in b_head(check->bi) buffer.
*/ */
if (check->bi->i < check->bi->size) if (b_data(check->bi) < check->bi->size)
check->bi->data[check->bi->i] = '\0'; b_head(check->bi)[b_data(check->bi)] = '\0';
else { else {
check->bi->data[check->bi->i - 1] = '\0'; b_head(check->bi)[b_data(check->bi) - 1] = '\0';
done = 1; /* buffer full, don't wait for more data */ done = 1; /* buffer full, don't wait for more data */
} }
/* Run the checks... */ /* Run the checks... */
switch (check->type) { switch (check->type) {
case PR_O2_HTTP_CHK: case PR_O2_HTTP_CHK:
if (!done && check->bi->i < strlen("HTTP/1.0 000\r")) if (!done && b_data(check->bi) < strlen("HTTP/1.0 000\r"))
goto wait_more_data; goto wait_more_data;
/* Check if the server speaks HTTP 1.X */ /* Check if the server speaks HTTP 1.X */
if ((check->bi->i < strlen("HTTP/1.0 000\r")) || if ((b_data(check->bi) < strlen("HTTP/1.0 000\r")) ||
(memcmp(check->bi->data, "HTTP/1.", 7) != 0 || (memcmp(b_head(check->bi), "HTTP/1.", 7) != 0 ||
(*(check->bi->data + 12) != ' ' && *(check->bi->data + 12) != '\r')) || (*(b_head(check->bi) + 12) != ' ' && *(b_head(check->bi) + 12) != '\r')) ||
!isdigit((unsigned char) *(check->bi->data + 9)) || !isdigit((unsigned char) *(check->bi->data + 10)) || !isdigit((unsigned char) *(b_head(check->bi) + 9)) || !isdigit((unsigned char) *(b_head(check->bi) + 10)) ||
!isdigit((unsigned char) *(check->bi->data + 11))) { !isdigit((unsigned char) *(b_head(check->bi) + 11))) {
cut_crlf(check->bi->data); cut_crlf(b_head(check->bi));
set_server_check_status(check, HCHK_STATUS_L7RSP, check->bi->data); set_server_check_status(check, HCHK_STATUS_L7RSP, b_head(check->bi));
goto out_wakeup; goto out_wakeup;
} }
check->code = str2uic(check->bi->data + 9); check->code = str2uic(b_head(check->bi) + 9);
desc = ltrim(check->bi->data + 12, ' '); desc = ltrim(b_head(check->bi) + 12, ' ');
if ((s->proxy->options & PR_O_DISABLE404) && if ((s->proxy->options & PR_O_DISABLE404) &&
(s->next_state != SRV_ST_STOPPED) && (check->code == 404)) { (s->next_state != SRV_ST_STOPPED) && (check->code == 404)) {
@ -882,7 +882,7 @@ static void event_srv_chk_r(struct conn_stream *cs)
goto wait_more_data; goto wait_more_data;
} }
/* check the reply : HTTP/1.X 2xx and 3xx are OK */ /* check the reply : HTTP/1.X 2xx and 3xx are OK */
else if (*(check->bi->data + 9) == '2' || *(check->bi->data + 9) == '3') { else if (*(b_head(check->bi) + 9) == '2' || *(b_head(check->bi) + 9) == '3') {
cut_crlf(desc); cut_crlf(desc);
set_server_check_status(check, HCHK_STATUS_L7OKD, desc); set_server_check_status(check, HCHK_STATUS_L7OKD, desc);
} }
@ -893,37 +893,37 @@ static void event_srv_chk_r(struct conn_stream *cs)
break; break;
case PR_O2_SSL3_CHK: case PR_O2_SSL3_CHK:
if (!done && check->bi->i < 5) if (!done && b_data(check->bi) < 5)
goto wait_more_data; goto wait_more_data;
/* Check for SSLv3 alert or handshake */ /* Check for SSLv3 alert or handshake */
if ((check->bi->i >= 5) && (*check->bi->data == 0x15 || *check->bi->data == 0x16)) if ((b_data(check->bi) >= 5) && (*b_head(check->bi) == 0x15 || *b_head(check->bi) == 0x16))
set_server_check_status(check, HCHK_STATUS_L6OK, NULL); set_server_check_status(check, HCHK_STATUS_L6OK, NULL);
else else
set_server_check_status(check, HCHK_STATUS_L6RSP, NULL); set_server_check_status(check, HCHK_STATUS_L6RSP, NULL);
break; break;
case PR_O2_SMTP_CHK: case PR_O2_SMTP_CHK:
if (!done && check->bi->i < strlen("000\r")) if (!done && b_data(check->bi) < strlen("000\r"))
goto wait_more_data; goto wait_more_data;
/* Check if the server speaks SMTP */ /* Check if the server speaks SMTP */
if ((check->bi->i < strlen("000\r")) || if ((b_data(check->bi) < strlen("000\r")) ||
(*(check->bi->data + 3) != ' ' && *(check->bi->data + 3) != '\r') || (*(b_head(check->bi) + 3) != ' ' && *(b_head(check->bi) + 3) != '\r') ||
!isdigit((unsigned char) *check->bi->data) || !isdigit((unsigned char) *(check->bi->data + 1)) || !isdigit((unsigned char) *b_head(check->bi)) || !isdigit((unsigned char) *(b_head(check->bi) + 1)) ||
!isdigit((unsigned char) *(check->bi->data + 2))) { !isdigit((unsigned char) *(b_head(check->bi) + 2))) {
cut_crlf(check->bi->data); cut_crlf(b_head(check->bi));
set_server_check_status(check, HCHK_STATUS_L7RSP, check->bi->data); set_server_check_status(check, HCHK_STATUS_L7RSP, b_head(check->bi));
goto out_wakeup; goto out_wakeup;
} }
check->code = str2uic(check->bi->data); check->code = str2uic(b_head(check->bi));
desc = ltrim(check->bi->data + 3, ' '); desc = ltrim(b_head(check->bi) + 3, ' ');
cut_crlf(desc); cut_crlf(desc);
/* Check for SMTP code 2xx (should be 250) */ /* Check for SMTP code 2xx (should be 250) */
if (*check->bi->data == '2') if (*b_head(check->bi) == '2')
set_server_check_status(check, HCHK_STATUS_L7OKD, desc); set_server_check_status(check, HCHK_STATUS_L7OKD, desc);
else else
set_server_check_status(check, HCHK_STATUS_L7STS, desc); set_server_check_status(check, HCHK_STATUS_L7STS, desc);
@ -963,7 +963,7 @@ static void event_srv_chk_r(struct conn_stream *cs)
* same category appear, the last one wins. * same category appear, the last one wins.
*/ */
p = check->bi->data; p = b_head(check->bi);
while (*p && *p != '\n' && *p != '\r') while (*p && *p != '\n' && *p != '\r')
p++; p++;
@ -977,7 +977,7 @@ static void event_srv_chk_r(struct conn_stream *cs)
} }
*p = 0; *p = 0;
cmd = check->bi->data; cmd = b_head(check->bi);
while (*cmd) { while (*cmd) {
/* look for next word */ /* look for next word */
@ -1135,15 +1135,15 @@ static void event_srv_chk_r(struct conn_stream *cs)
} }
case PR_O2_PGSQL_CHK: case PR_O2_PGSQL_CHK:
if (!done && check->bi->i < 9) if (!done && b_data(check->bi) < 9)
goto wait_more_data; goto wait_more_data;
if (check->bi->data[0] == 'R') { if (b_head(check->bi)[0] == 'R') {
set_server_check_status(check, HCHK_STATUS_L7OKD, "PostgreSQL server is ok"); set_server_check_status(check, HCHK_STATUS_L7OKD, "PostgreSQL server is ok");
} }
else { else {
if ((check->bi->data[0] == 'E') && (check->bi->data[5]!=0) && (check->bi->data[6]!=0)) if ((b_head(check->bi)[0] == 'E') && (b_head(check->bi)[5]!=0) && (b_head(check->bi)[6]!=0))
desc = &check->bi->data[6]; desc = &b_head(check->bi)[6];
else else
desc = "PostgreSQL unknown error"; desc = "PostgreSQL unknown error";
@ -1152,29 +1152,29 @@ static void event_srv_chk_r(struct conn_stream *cs)
break; break;
case PR_O2_REDIS_CHK: case PR_O2_REDIS_CHK:
if (!done && check->bi->i < 7) if (!done && b_data(check->bi) < 7)
goto wait_more_data; goto wait_more_data;
if (strcmp(check->bi->data, "+PONG\r\n") == 0) { if (strcmp(b_head(check->bi), "+PONG\r\n") == 0) {
set_server_check_status(check, HCHK_STATUS_L7OKD, "Redis server is ok"); set_server_check_status(check, HCHK_STATUS_L7OKD, "Redis server is ok");
} }
else { else {
set_server_check_status(check, HCHK_STATUS_L7STS, check->bi->data); set_server_check_status(check, HCHK_STATUS_L7STS, b_head(check->bi));
} }
break; break;
case PR_O2_MYSQL_CHK: case PR_O2_MYSQL_CHK:
if (!done && check->bi->i < 5) if (!done && b_data(check->bi) < 5)
goto wait_more_data; goto wait_more_data;
if (s->proxy->check_len == 0) { // old mode if (s->proxy->check_len == 0) { // old mode
if (*(check->bi->data + 4) != '\xff') { if (*(b_head(check->bi) + 4) != '\xff') {
/* We set the MySQL Version in description for information purpose /* We set the MySQL Version in description for information purpose
* FIXME : it can be cool to use MySQL Version for other purpose, * FIXME : it can be cool to use MySQL Version for other purpose,
* like mark as down old MySQL server. * like mark as down old MySQL server.
*/ */
if (check->bi->i > 51) { if (b_data(check->bi) > 51) {
desc = ltrim(check->bi->data + 5, ' '); desc = ltrim(b_head(check->bi) + 5, ' ');
set_server_check_status(check, HCHK_STATUS_L7OKD, desc); set_server_check_status(check, HCHK_STATUS_L7OKD, desc);
} }
else { else {
@ -1184,48 +1184,48 @@ static void event_srv_chk_r(struct conn_stream *cs)
/* it seems we have a OK packet but without a valid length, /* it seems we have a OK packet but without a valid length,
* it must be a protocol error * it must be a protocol error
*/ */
set_server_check_status(check, HCHK_STATUS_L7RSP, check->bi->data); set_server_check_status(check, HCHK_STATUS_L7RSP, b_head(check->bi));
} }
} }
else { else {
/* An error message is attached in the Error packet */ /* An error message is attached in the Error packet */
desc = ltrim(check->bi->data + 7, ' '); desc = ltrim(b_head(check->bi) + 7, ' ');
set_server_check_status(check, HCHK_STATUS_L7STS, desc); set_server_check_status(check, HCHK_STATUS_L7STS, desc);
} }
} else { } else {
unsigned int first_packet_len = ((unsigned int) *check->bi->data) + unsigned int first_packet_len = ((unsigned int) *b_head(check->bi)) +
(((unsigned int) *(check->bi->data + 1)) << 8) + (((unsigned int) *(b_head(check->bi) + 1)) << 8) +
(((unsigned int) *(check->bi->data + 2)) << 16); (((unsigned int) *(b_head(check->bi) + 2)) << 16);
if (check->bi->i == first_packet_len + 4) { if (b_data(check->bi) == first_packet_len + 4) {
/* MySQL Error packet always begin with field_count = 0xff */ /* MySQL Error packet always begin with field_count = 0xff */
if (*(check->bi->data + 4) != '\xff') { if (*(b_head(check->bi) + 4) != '\xff') {
/* We have only one MySQL packet and it is a Handshake Initialization packet /* We have only one MySQL packet and it is a Handshake Initialization packet
* but we need to have a second packet to know if it is alright * but we need to have a second packet to know if it is alright
*/ */
if (!done && check->bi->i < first_packet_len + 5) if (!done && b_data(check->bi) < first_packet_len + 5)
goto wait_more_data; goto wait_more_data;
} }
else { else {
/* We have only one packet and it is an Error packet, /* We have only one packet and it is an Error packet,
* an error message is attached, so we can display it * an error message is attached, so we can display it
*/ */
desc = &check->bi->data[7]; desc = &b_head(check->bi)[7];
//ha_warning("onlyoneERR: %s\n", desc); //ha_warning("onlyoneERR: %s\n", desc);
set_server_check_status(check, HCHK_STATUS_L7STS, desc); set_server_check_status(check, HCHK_STATUS_L7STS, desc);
} }
} else if (check->bi->i > first_packet_len + 4) { } else if (b_data(check->bi) > first_packet_len + 4) {
unsigned int second_packet_len = ((unsigned int) *(check->bi->data + first_packet_len + 4)) + unsigned int second_packet_len = ((unsigned int) *(b_head(check->bi) + first_packet_len + 4)) +
(((unsigned int) *(check->bi->data + first_packet_len + 5)) << 8) + (((unsigned int) *(b_head(check->bi) + first_packet_len + 5)) << 8) +
(((unsigned int) *(check->bi->data + first_packet_len + 6)) << 16); (((unsigned int) *(b_head(check->bi) + first_packet_len + 6)) << 16);
if (check->bi->i == first_packet_len + 4 + second_packet_len + 4 ) { if (b_data(check->bi) == first_packet_len + 4 + second_packet_len + 4 ) {
/* We have 2 packets and that's good */ /* We have 2 packets and that's good */
/* Check if the second packet is a MySQL Error packet or not */ /* Check if the second packet is a MySQL Error packet or not */
if (*(check->bi->data + first_packet_len + 8) != '\xff') { if (*(b_head(check->bi) + first_packet_len + 8) != '\xff') {
/* No error packet */ /* No error packet */
/* We set the MySQL Version in description for information purpose */ /* We set the MySQL Version in description for information purpose */
desc = &check->bi->data[5]; desc = &b_head(check->bi)[5];
//ha_warning("2packetOK: %s\n", desc); //ha_warning("2packetOK: %s\n", desc);
set_server_check_status(check, HCHK_STATUS_L7OKD, desc); set_server_check_status(check, HCHK_STATUS_L7OKD, desc);
} }
@ -1233,7 +1233,7 @@ static void event_srv_chk_r(struct conn_stream *cs)
/* An error message is attached in the Error packet /* An error message is attached in the Error packet
* so we can display it ! :) * so we can display it ! :)
*/ */
desc = &check->bi->data[first_packet_len+11]; desc = &b_head(check->bi)[first_packet_len+11];
//ha_warning("2packetERR: %s\n", desc); //ha_warning("2packetERR: %s\n", desc);
set_server_check_status(check, HCHK_STATUS_L7STS, desc); set_server_check_status(check, HCHK_STATUS_L7STS, desc);
} }
@ -1246,7 +1246,7 @@ static void event_srv_chk_r(struct conn_stream *cs)
/* it seems we have a Handshake Initialization packet but without a valid length, /* it seems we have a Handshake Initialization packet but without a valid length,
* it must be a protocol error * it must be a protocol error
*/ */
desc = &check->bi->data[5]; desc = &b_head(check->bi)[5];
//ha_warning("protoerr: %s\n", desc); //ha_warning("protoerr: %s\n", desc);
set_server_check_status(check, HCHK_STATUS_L7RSP, desc); set_server_check_status(check, HCHK_STATUS_L7RSP, desc);
} }
@ -1254,7 +1254,7 @@ static void event_srv_chk_r(struct conn_stream *cs)
break; break;
case PR_O2_LDAP_CHK: case PR_O2_LDAP_CHK:
if (!done && check->bi->i < 14) if (!done && b_data(check->bi) < 14)
goto wait_more_data; goto wait_more_data;
/* Check if the server speaks LDAP (ASN.1/BER) /* Check if the server speaks LDAP (ASN.1/BER)
@ -1265,31 +1265,31 @@ static void event_srv_chk_r(struct conn_stream *cs)
/* http://tools.ietf.org/html/rfc4511#section-4.1.1 /* http://tools.ietf.org/html/rfc4511#section-4.1.1
* LDAPMessage: 0x30: SEQUENCE * LDAPMessage: 0x30: SEQUENCE
*/ */
if ((check->bi->i < 14) || (*(check->bi->data) != '\x30')) { if ((b_data(check->bi) < 14) || (*(b_head(check->bi)) != '\x30')) {
set_server_check_status(check, HCHK_STATUS_L7RSP, "Not LDAPv3 protocol"); set_server_check_status(check, HCHK_STATUS_L7RSP, "Not LDAPv3 protocol");
} }
else { else {
/* size of LDAPMessage */ /* size of LDAPMessage */
msglen = (*(check->bi->data + 1) & 0x80) ? (*(check->bi->data + 1) & 0x7f) : 0; msglen = (*(b_head(check->bi) + 1) & 0x80) ? (*(b_head(check->bi) + 1) & 0x7f) : 0;
/* http://tools.ietf.org/html/rfc4511#section-4.2.2 /* http://tools.ietf.org/html/rfc4511#section-4.2.2
* messageID: 0x02 0x01 0x01: INTEGER 1 * messageID: 0x02 0x01 0x01: INTEGER 1
* protocolOp: 0x61: bindResponse * protocolOp: 0x61: bindResponse
*/ */
if ((msglen > 2) || if ((msglen > 2) ||
(memcmp(check->bi->data + 2 + msglen, "\x02\x01\x01\x61", 4) != 0)) { (memcmp(b_head(check->bi) + 2 + msglen, "\x02\x01\x01\x61", 4) != 0)) {
set_server_check_status(check, HCHK_STATUS_L7RSP, "Not LDAPv3 protocol"); set_server_check_status(check, HCHK_STATUS_L7RSP, "Not LDAPv3 protocol");
goto out_wakeup; goto out_wakeup;
} }
/* size of bindResponse */ /* size of bindResponse */
msglen += (*(check->bi->data + msglen + 6) & 0x80) ? (*(check->bi->data + msglen + 6) & 0x7f) : 0; msglen += (*(b_head(check->bi) + msglen + 6) & 0x80) ? (*(b_head(check->bi) + msglen + 6) & 0x7f) : 0;
/* http://tools.ietf.org/html/rfc4511#section-4.1.9 /* http://tools.ietf.org/html/rfc4511#section-4.1.9
* ldapResult: 0x0a 0x01: ENUMERATION * ldapResult: 0x0a 0x01: ENUMERATION
*/ */
if ((msglen > 4) || if ((msglen > 4) ||
(memcmp(check->bi->data + 7 + msglen, "\x0a\x01", 2) != 0)) { (memcmp(b_head(check->bi) + 7 + msglen, "\x0a\x01", 2) != 0)) {
set_server_check_status(check, HCHK_STATUS_L7RSP, "Not LDAPv3 protocol"); set_server_check_status(check, HCHK_STATUS_L7RSP, "Not LDAPv3 protocol");
goto out_wakeup; goto out_wakeup;
} }
@ -1297,7 +1297,7 @@ static void event_srv_chk_r(struct conn_stream *cs)
/* http://tools.ietf.org/html/rfc4511#section-4.1.9 /* http://tools.ietf.org/html/rfc4511#section-4.1.9
* resultCode * resultCode
*/ */
check->code = *(check->bi->data + msglen + 9); check->code = *(b_head(check->bi) + msglen + 9);
if (check->code) { if (check->code) {
set_server_check_status(check, HCHK_STATUS_L7STS, "See RFC: http://tools.ietf.org/html/rfc4511#section-4.1.9"); set_server_check_status(check, HCHK_STATUS_L7STS, "See RFC: http://tools.ietf.org/html/rfc4511#section-4.1.9");
} else { } else {
@ -1310,16 +1310,16 @@ static void event_srv_chk_r(struct conn_stream *cs)
unsigned int framesz; unsigned int framesz;
char err[HCHK_DESC_LEN]; char err[HCHK_DESC_LEN];
if (!done && check->bi->i < 4) if (!done && b_data(check->bi) < 4)
goto wait_more_data; goto wait_more_data;
memcpy(&framesz, check->bi->data, 4); memcpy(&framesz, b_head(check->bi), 4);
framesz = ntohl(framesz); framesz = ntohl(framesz);
if (!done && check->bi->i < (4+framesz)) if (!done && b_data(check->bi) < (4+framesz))
goto wait_more_data; goto wait_more_data;
if (!spoe_handle_healthcheck_response(check->bi->data+4, framesz, err, HCHK_DESC_LEN-1)) if (!spoe_handle_healthcheck_response(b_head(check->bi)+4, framesz, err, HCHK_DESC_LEN-1))
set_server_check_status(check, HCHK_STATUS_L7OKD, "SPOA server is ok"); set_server_check_status(check, HCHK_STATUS_L7OKD, "SPOA server is ok");
else else
set_server_check_status(check, HCHK_STATUS_L7STS, err); set_server_check_status(check, HCHK_STATUS_L7STS, err);
@ -1337,8 +1337,8 @@ static void event_srv_chk_r(struct conn_stream *cs)
chk_report_conn_err(check, 0, 0); chk_report_conn_err(check, 0, 0);
/* Reset the check buffer... */ /* Reset the check buffer... */
*check->bi->data = '\0'; *b_head(check->bi) = '\0';
check->bi->i = 0; b_reset(check->bi);
/* Close the connection... We still attempt to nicely close if, /* Close the connection... We still attempt to nicely close if,
* for instance, SSL needs to send a "close notify." Later, we perform * for instance, SSL needs to send a "close notify." Later, we perform
@ -1526,7 +1526,7 @@ static int connect_conn_chk(struct task *t)
if ((check->type) == PR_O2_SSL3_CHK) { if ((check->type) == PR_O2_SSL3_CHK) {
/* SSL requires that we put Unix time in the request */ /* SSL requires that we put Unix time in the request */
int gmt_time = htonl(date.tv_sec); int gmt_time = htonl(date.tv_sec);
memcpy(check->bo->data + 11, &gmt_time, 4); memcpy(b_head(check->bo) + 11, &gmt_time, 4);
} }
else if ((check->type) == PR_O2_HTTP_CHK) { else if ((check->type) == PR_O2_HTTP_CHK) {
if (s->proxy->options2 & PR_O2_CHK_SNDST) if (s->proxy->options2 & PR_O2_CHK_SNDST)
@ -1535,7 +1535,7 @@ static int connect_conn_chk(struct task *t)
if (s->proxy->options2 & PR_O2_EXP_TYPE) if (s->proxy->options2 & PR_O2_EXP_TYPE)
bo_putstr(check->bo, "Connection: close\r\n"); bo_putstr(check->bo, "Connection: close\r\n");
bo_putstr(check->bo, "\r\n"); bo_putstr(check->bo, "\r\n");
*check->bo->p = '\0'; /* to make gdb output easier to read */ *b_tail(check->bo) = '\0'; /* to make gdb output easier to read */
} }
} }
@ -2129,10 +2129,8 @@ static struct task *process_chk_conn(struct task *t, void *context, unsigned sho
set_server_check_status(check, HCHK_STATUS_START, NULL); set_server_check_status(check, HCHK_STATUS_START, NULL);
check->state |= CHK_ST_INPROGRESS; check->state |= CHK_ST_INPROGRESS;
check->bi->p = check->bi->data; b_reset(check->bi);
check->bi->i = 0; b_reset(check->bo);
check->bo->p = check->bo->data;
check->bo->o = 0;
ret = connect_conn_chk(t); ret = connect_conn_chk(t);
cs = check->cs; cs = check->cs;
@ -2426,8 +2424,8 @@ static int httpchk_expect(struct server *s, int done)
switch (s->proxy->options2 & PR_O2_EXP_TYPE) { switch (s->proxy->options2 & PR_O2_EXP_TYPE) {
case PR_O2_EXP_STS: case PR_O2_EXP_STS:
case PR_O2_EXP_RSTS: case PR_O2_EXP_RSTS:
memcpy(status_code, s->check.bi->data + 9, 3); memcpy(status_code, b_head(s->check.bi) + 9, 3);
memcpy(status_msg + strlen(status_msg) - 4, s->check.bi->data + 9, 3); memcpy(status_msg + strlen(status_msg) - 4, b_head(s->check.bi) + 9, 3);
if ((s->proxy->options2 & PR_O2_EXP_TYPE) == PR_O2_EXP_STS) if ((s->proxy->options2 & PR_O2_EXP_TYPE) == PR_O2_EXP_STS)
ret = strncmp(s->proxy->expect_str, status_code, 3) == 0; ret = strncmp(s->proxy->expect_str, status_code, 3) == 0;
@ -2448,7 +2446,7 @@ static int httpchk_expect(struct server *s, int done)
* to '\0' if crlf < 2. * to '\0' if crlf < 2.
*/ */
crlf = 0; crlf = 0;
for (contentptr = s->check.bi->data; *contentptr; contentptr++) { for (contentptr = b_head(s->check.bi); *contentptr; contentptr++) {
if (crlf >= 2) if (crlf >= 2)
break; break;
if (*contentptr == '\r') if (*contentptr == '\r')
@ -2647,10 +2645,8 @@ static int tcpcheck_main(struct check *check)
/* no step means first step initialisation */ /* no step means first step initialisation */
if (check->current_step == NULL) { if (check->current_step == NULL) {
check->last_started_step = NULL; check->last_started_step = NULL;
check->bo->p = check->bo->data; b_reset(check->bo);
check->bo->o = 0; b_reset(check->bi);
check->bi->p = check->bi->data;
check->bi->i = 0;
check->current_step = next; check->current_step = next;
t->expire = tick_add(now_ms, MS_TO_TICKS(check->inter)); t->expire = tick_add(now_ms, MS_TO_TICKS(check->inter));
if (s->proxy->timeout.check) if (s->proxy->timeout.check)
@ -2667,14 +2663,14 @@ static int tcpcheck_main(struct check *check)
* in the remaining space. That explains why we break out of the * in the remaining space. That explains why we break out of the
* loop after this control. If we have data, conn is valid. * loop after this control. If we have data, conn is valid.
*/ */
if (check->bo->o && if (b_data(check->bo) &&
(&check->current_step->list == head || (&check->current_step->list == head ||
check->current_step->action != TCPCHK_ACT_SEND || check->current_step->action != TCPCHK_ACT_SEND ||
check->current_step->string_len >= b_room(check->bo))) { check->current_step->string_len >= b_room(check->bo))) {
int ret; int ret;
__cs_want_send(cs); __cs_want_send(cs);
ret = conn->mux->snd_buf(cs, check->bo, check->bo->o, 0); ret = conn->mux->snd_buf(cs, check->bo, b_data(check->bo), 0);
b_del(check->bo, ret); b_del(check->bo, ret);
b_realign_if_empty(check->bo); b_realign_if_empty(check->bo);
@ -2849,9 +2845,9 @@ static int tcpcheck_main(struct check *check)
check->last_started_step = check->current_step; check->last_started_step = check->current_step;
/* reset the read buffer */ /* reset the read buffer */
if (*check->bi->data != '\0') { if (*b_head(check->bi) != '\0') {
*check->bi->data = '\0'; *b_head(check->bi) = '\0';
check->bi->i = 0; b_reset(check->bi);
} }
if (conn->flags & CO_FL_SOCK_WR_SH) { if (conn->flags & CO_FL_SOCK_WR_SH) {
@ -2873,7 +2869,7 @@ static int tcpcheck_main(struct check *check)
continue; continue;
bo_putblk(check->bo, check->current_step->string, check->current_step->string_len); bo_putblk(check->bo, check->current_step->string, check->current_step->string_len);
*check->bo->p = '\0'; /* to make gdb output easier to read */ *b_tail(check->bo) = '\0'; /* to make gdb output easier to read */
/* go to next rule and try to send */ /* go to next rule and try to send */
check->current_step = LIST_NEXT(&check->current_step->list, struct tcpcheck_rule *, list); check->current_step = LIST_NEXT(&check->current_step->list, struct tcpcheck_rule *, list);
@ -2892,7 +2888,7 @@ static int tcpcheck_main(struct check *check)
if (conn->mux->rcv_buf(cs, check->bi, check->bi->size, 0) <= 0) { if (conn->mux->rcv_buf(cs, check->bi, check->bi->size, 0) <= 0) {
if (conn->flags & (CO_FL_ERROR | CO_FL_SOCK_RD_SH) || cs->flags & CS_FL_ERROR) { if (conn->flags & (CO_FL_ERROR | CO_FL_SOCK_RD_SH) || cs->flags & CS_FL_ERROR) {
done = 1; done = 1;
if ((conn->flags & CO_FL_ERROR || cs->flags & CS_FL_ERROR) && !check->bi->i) { if ((conn->flags & CO_FL_ERROR || cs->flags & CS_FL_ERROR) && !b_data(check->bi)) {
/* Report network errors only if we got no other data. Otherwise /* Report network errors only if we got no other data. Otherwise
* we'll let the upper layers decide whether the response is OK * we'll let the upper layers decide whether the response is OK
* or not. It is very common that an RST sent by the server is * or not. It is very common that an RST sent by the server is
@ -2911,20 +2907,20 @@ static int tcpcheck_main(struct check *check)
/* Intermediate or complete response received. /* Intermediate or complete response received.
* Terminate string in check->bi->data buffer. * Terminate string in b_head(check->bi) buffer.
*/ */
if (check->bi->i < check->bi->size) { if (b_data(check->bi) < check->bi->size) {
check->bi->data[check->bi->i] = '\0'; b_head(check->bi)[b_data(check->bi)] = '\0';
} }
else { else {
check->bi->data[check->bi->i - 1] = '\0'; b_head(check->bi)[b_data(check->bi) - 1] = '\0';
done = 1; /* buffer full, don't wait for more data */ done = 1; /* buffer full, don't wait for more data */
} }
contentptr = check->bi->data; contentptr = b_head(check->bi);
/* Check that response body is not empty... */ /* Check that response body is not empty... */
if (!check->bi->i) { if (!b_data(check->bi)) {
if (!done) if (!done)
continue; continue;
@ -2939,12 +2935,12 @@ static int tcpcheck_main(struct check *check)
goto out_end_tcpcheck; goto out_end_tcpcheck;
} }
if (!done && (check->current_step->string != NULL) && (check->bi->i < check->current_step->string_len) ) if (!done && (check->current_step->string != NULL) && (b_data(check->bi) < check->current_step->string_len) )
continue; /* try to read more */ continue; /* try to read more */
tcpcheck_expect: tcpcheck_expect:
if (check->current_step->string != NULL) if (check->current_step->string != NULL)
ret = my_memmem(contentptr, check->bi->i, check->current_step->string, check->current_step->string_len) != NULL; ret = my_memmem(contentptr, b_data(check->bi), check->current_step->string, check->current_step->string_len) != NULL;
else if (check->current_step->expect_regex != NULL) else if (check->current_step->expect_regex != NULL)
ret = regex_exec(check->current_step->expect_regex, contentptr); ret = regex_exec(check->current_step->expect_regex, contentptr);
@ -3052,13 +3048,13 @@ static int tcpcheck_main(struct check *check)
/* We're waiting for some I/O to complete, we've reached the end of the /* We're waiting for some I/O to complete, we've reached the end of the
* rules, or both. Do what we have to do, otherwise we're done. * rules, or both. Do what we have to do, otherwise we're done.
*/ */
if (&check->current_step->list == head && !check->bo->o) { if (&check->current_step->list == head && !b_data(check->bo)) {
set_server_check_status(check, HCHK_STATUS_L7OKD, "(tcp-check)"); set_server_check_status(check, HCHK_STATUS_L7OKD, "(tcp-check)");
goto out_end_tcpcheck; goto out_end_tcpcheck;
} }
/* warning, current_step may now point to the head */ /* warning, current_step may now point to the head */
if (check->bo->o) if (b_data(check->bo))
__cs_want_send(cs); __cs_want_send(cs);
if (&check->current_step->list != head && if (&check->current_step->list != head &&