Understand the binary protocol for prepared statements. This section details how prepared statements are exchanged efficiently between client and server, optimizing performance and security.
Closes a previously prepared statement.
Client to server.
05 00 00 00 19 04 00 00 00
No response from server.
This page is licensed: CC BY-SA / Gnu FDL
Executes a bulk insert of a previously prepared statement.
A command that returns a result set returns an error (Error packet).
Client to server.
int<1> 0xfa
: COM_STMT_BULK_EXECUTE
header.
int<4> statement id.
If (bulk_flag
& SEND_TYPES_TO_SERVER
):
For each parameter:
byte<1>: field type.
byte<1>: parameter type flag.
Until end of packet:
For each parameter (i.e param_count
times):
byte<1>: parameter indicator.
If indicator == NONE
:
byte : binary parameter value.
SEND_UNIT_RESULTS
64
Return generated affected rows and auto-increment IDs as a result set (only when server supports MARIADB_CLIENT_BULK_UNIT_RESULTS
capability).
SEND_TYPES_TO_SERVER
128
Send types to server.
128
unsigned
0
NONE
Value follow
1
NULL
Value is null
2
DEFAULT
For INSERT/UPDATE, value is default
3
IGNORE
Value is default for insert, Is ignored for update
The server can answer with 3 different responses:
0xff: ERR_Packet if any errors occur.
0x00: OK_packet when query execution works without result set.
A result set containing affected rows and auto-increment IDs when bulk flag SEND_UNIT_RESULTS
is set.
This page is licensed: CC BY-SA / Gnu FDL
Executes a previously prepared statement.
If specific data is large, it can be sent separately prior to this command (see COM_STMT_SEND_LONG_DATA).
If a statement is re-executed without changing the bind types, the types do not need to be sent to the server again.
Client to server.
int<1> 0x17
: COM_STMT_EXECUTE
header.
int<1> flags.
int<4> Iteration count (always 1).
If (param_count
> 0
)
byte<(param_count + 7)/8> null bitmap.
byte<1>: send type to server (0 / 1).
If (send type to server):
For each parameter:
byte<1>: field type.
byte<1>: parameter flag.
For each parameter (for instance, param_count
times):
If parameter is not null:
byte binary parameter value.
Statement ID is the identifier of the prepared statement (from COM_STMT_PREPARE answer).
Value -1
(0xFFFFFFFF
) can be used to indicate to use the last statement prepared on current connection if no COM_STMT_PREPARE
has failed since.
This permit pipelining :
Send COM_STMT_PREPARE
+ COM_STMT_EXECUTE
with statement ID -1
.
Read COM_STMT_PREPARE
+ COM_STMT_EXECUTE
response.
In case COM_STMT_PREPARE
returns an error, COM_STMT_EXECUTE
returns an error that statement ID -1
is unknown. This permits to avoid much of the network latency.
0
no cursor
1
read only
2
cursor for update
4
scrollable cursor
If the flags of the COM_STMT_EXECUTE
request a cursor to be opened, the returned result only contains the column definitions and the EOF
that terminates it, and the result set rows are fetched using separate COM_STMT_FETCH
commands.
Whether a cursor is actually opened is indicated by the SERVER_STATUS_CURSOR_EXISTS
bit in the first EOF packet in the response to the COM_STMT_EXECUTE
. If it is not set in, no cursor is opened and a normal result set is returned.
Parameter type flag byte:
128
unsigned
The NULL-Bitmap
indicates if parameters are null (one bit per parameter). If the parameter is NULL
, the bit is set in the bitmap and the parameter value is not sent.
The size in bytes of the NULL-bitmap
can be calculated with: (parameter number + 7) / 8
The encoding of the COM_STMT_EXECUTE
parameters are the same as the encoding of the binary result sets.
The server can answer with 3 different responses:
0xff
: ERR_Packet if any errors occur.
0x00
: OK_packet when query execution works without result set.
One (or more) result set, when query execution return rows (in case of SELECT
query, for example).
This page is licensed: CC BY-SA / Gnu FDL
Fetch rows from a prepared statement.
A COM_STMT_EXECUTE with a non-zero cursor flag must have been successfully executed before any COM_STMT_FETCH
commands can be executed.
Returns one or more binary result set rows followed by an EOF packet.
This page is licensed: CC BY-SA / Gnu FDL
Prepares a statement on the server.
1F 00 00 00 16 53 45 4C 45 43 54 20 2A 20 46 52 .....SELECT * FR
1F 4D 20 74 65 73 74 5F 62 69 6E 64 5F 72 65 73 OM test_bind_res
75 6C 74 ult
If anything goes wrong, the server will send an ERR_Packet. If the command succeeds, different packets are received:
If number of parameters (count of '?' placeholders) > 0
:
For each parameter:
If !DEPRECATE_EOF
eof_packet.
If prepared statement returns result set and number of result set columns > 0
:
For each column:
If !DEPRECATE_EOF
eof_packet.
int<1> 0x00
COM_STMT_PREPARE_OK
header.
int<4> statement ID.
int<2> number of columns in the returned result set (or 0 if statement does not return result set).
int<2> number of prepared statement parameters ('?' placeholders).
string<1> -not used-
int<2> number of warnings.
This page is licensed: CC BY-SA / Gnu FDL
Resets a prepared statement on the client and server to state after preparing.
ERR_Packet or OK_Packet.
05 00 00 00 1A 04 00 00 00
This page is licensed: CC BY-SA / Gnu FDL
When data for a specific column is large, it can be sent separately to avoid the limitation of max_allowed_packet
(see packet splitting).
Multiple COM_STMT_SEND_LONG_DATA
commands with the same column ID append the data. COM_STMT_SEND_LONG_DATA
is sent before COM_STMT_EXECUTE.
Server doesn't send response.
This page is licensed: CC BY-SA / Gnu FDL
Understand server response packets in MariaDB's binary protocol for prepared statements. This section details the structure of responses from the server, crucial for client-side parsing and handling.
In contrast to the text protocol, the binary protocol transfers data according to the format of the field types returned in PACKET_METADATA
.
MYSQL_TYPE_BIT
str_LEC
MYSQL_TYPE_BLOB
str_LEC
MYSQL_TYPE_DATE MYSQL_TYPE_DATETIME MYSQL_TYPE_TIMESTAMP
int_11 (default)int_7 (no microseconds)int_4 (no time values)int_0 (no values)
MYSQL_TYPE_DECIMAL
str_LEC
MYSQL_TYPE_DOUBLE
int_8
MYSQL_TYPE_ENUM
str_LEC
MYSQL_TYPE_FLOAT
int_4
MYSQL_TYPE_GEOMETRY
str_LEC
MYSQL_TYPE_INT24
int_4
MYSQL_TYPE_JSON
str_LEC
MYSQL_TYPE_LONGLONG
int_8
MYSQL_TYPE_LONG_BLOB
str_LEC
MYSQL_TYPE_LONG
int_4
MYSQL_TYPE_MEDIUM_BLOB
str_LEC
MYSQL_TYPE_NEWDECIMAL
str_LEC
MYSQL_TYPE_NULL
stored in bitmap
MYSQL_TYPE_SET
str_LEC
MYSQL_TYPE_STRING
str_LEC
MYSQL_TYPE_SHORT
int_2
MYSQL_TYPE_TINY_BLOB
str_LEC
MYSQL_TYPE_TINY
int_1
MYSQL_TYPE_VARCHAR
str_LEC
MYSQL_TYPE_VAR_STRING
str_LEC
MYSQL_TYPE_YEAR
int_4
(column_count + 7)/8 null bitmap
while (!eof) {
for (i=0; i < column_count; i++)
{
data (length depends on the data type)
}
}
This page is licensed: CC BY-SA / Gnu FDL