mirror of
https://github.com/mariadb-corporation/mariadb-connector-c.git
synced 2025-08-16 17:15:01 +00:00
CONC-783 Fix potential loss of "Proxy header not accepted from host" error
Send the proxy header and handshake response in a single write. If the client uses two separate send() calls, the server's error message "Proxy header not accepted from host" may be lost. This occurs because the server sends a TCP RST (reset) instead of a FIN if it closes the socket while the client is still sending data. As a result, the client may receive ECONNRESET or EPIPE, without seeing the actual error from the server.
This commit is contained in:
@ -413,6 +413,7 @@ void ma_net_end(NET *net);
|
||||
void ma_net_clear(NET *net);
|
||||
int ma_net_flush(NET *net);
|
||||
int ma_net_write(NET *net,const unsigned char *packet, size_t len);
|
||||
int ma_net_write_buff(NET *net, const char *packet, size_t len);
|
||||
int ma_net_write_command(NET *net,unsigned char command,const char *packet,
|
||||
size_t len, my_bool disable_flush);
|
||||
int ma_net_real_write(NET *net,const char *packet, size_t len);
|
||||
|
@ -73,7 +73,7 @@ ulong net_buffer_length= 8192; /* Default length. Enlarged if necessary */
|
||||
** can't normally do this the client should have a bigger max-buffer.
|
||||
*/
|
||||
|
||||
static int ma_net_write_buff(NET *net,const char *packet, size_t len);
|
||||
int ma_net_write_buff(NET *net,const char *packet, size_t len);
|
||||
|
||||
|
||||
/* Init with packet info */
|
||||
@ -246,7 +246,7 @@ int ma_net_write_command(NET *net, uchar command,
|
||||
}
|
||||
|
||||
|
||||
static int ma_net_write_buff(NET *net,const char *packet, size_t len)
|
||||
int ma_net_write_buff(NET *net,const char *packet, size_t len)
|
||||
{
|
||||
size_t left_length;
|
||||
|
||||
|
@ -1783,17 +1783,6 @@ restart:
|
||||
goto error;
|
||||
}
|
||||
|
||||
if (mysql->options.extension && mysql->options.extension->proxy_header)
|
||||
{
|
||||
char *hdr = mysql->options.extension->proxy_header;
|
||||
size_t len = mysql->options.extension->proxy_header_len;
|
||||
if (ma_pvio_write(pvio, (unsigned char *)hdr, len) <= 0)
|
||||
{
|
||||
ma_pvio_close(pvio);
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
|
||||
if (ma_net_init(net, pvio))
|
||||
{
|
||||
ma_pvio_close(pvio);
|
||||
|
@ -208,6 +208,11 @@ static int send_client_reply_packet(MCPVIO_EXT *mpvio,
|
||||
char *buff, *end;
|
||||
size_t conn_attr_len= (mysql->options.extension) ?
|
||||
mysql->options.extension->connect_attrs_len : 0;
|
||||
size_t proxy_header_len= 0;
|
||||
char *proxy_header=
|
||||
(mysql->options.extension) ? mysql->options.extension->proxy_header : NULL;
|
||||
if (proxy_header)
|
||||
proxy_header_len= mysql->options.extension->proxy_header_len;
|
||||
|
||||
/* see end= buff+32 below, fixed size of the packet is 32 bytes */
|
||||
buff= malloc(33 + USERNAME_LENGTH + data_len + NAME_LEN + NAME_LEN + conn_attr_len + 9);
|
||||
@ -340,6 +345,9 @@ static int send_client_reply_packet(MCPVIO_EXT *mpvio,
|
||||
Send mysql->client_flag, max_packet_size - unencrypted otherwise
|
||||
the server does not know we want to do SSL
|
||||
*/
|
||||
if (proxy_header_len)
|
||||
ma_net_write_buff(net, proxy_header, proxy_header_len);
|
||||
|
||||
if (ma_net_write(net, (unsigned char *)buff, (size_t) (end-buff)) || ma_net_flush(net))
|
||||
{
|
||||
my_set_error(mysql, CR_SERVER_LOST, SQLSTATE_UNKNOWN,
|
||||
@ -417,6 +425,8 @@ static int send_client_reply_packet(MCPVIO_EXT *mpvio,
|
||||
*end++= compression_level;
|
||||
}
|
||||
|
||||
if (proxy_header_len)
|
||||
ma_net_write_buff(net, proxy_header, proxy_header_len);
|
||||
/* Write authentication package */
|
||||
if (ma_net_write(net, (unsigned char *)buff, (size_t) (end-buff)) || ma_net_flush(net))
|
||||
{
|
||||
|
Reference in New Issue
Block a user