@@ -1685,8 +1685,12 @@ impl MySerialize for HandshakePacket<'_> {
16851685 } else {
16861686 buf. put_u8 ( 0 ) ;
16871687 }
1688-
1689- buf. put_slice ( & [ 0_u8 ; 10 ] [ ..] ) ;
1688+ if self . mariadb_ext_capabilities . is_empty ( ) {
1689+ buf. put_slice ( & [ 0_u8 ; 10 ] [ ..] ) ;
1690+ } else {
1691+ buf. put_slice ( & [ 0_u8 ; 6 ] [ ..] ) ;
1692+ self . mariadb_ext_capabilities . serialize ( & mut * buf) ;
1693+ }
16901694
16911695 // Assume that the packet is well formed:
16921696 // * the CLIENT_SECURE_CONNECTION is set.
@@ -4135,6 +4139,71 @@ mod test {
41354139 assert_eq ! ( expected, actual) ;
41364140 }
41374141
4142+ #[ test]
4143+ fn should_parse_handshake_packet_with_mariadb_ext_capabilities ( ) {
4144+ const HSP : & [ u8 ] = b"\x0a 5.5.5-11.4.7-MariaDB-log\x00 \x0b \x00 \
4145+ \x00 \x00 \x64 \x76 \x48 \x40 \x49 \x2d \x43 \x4a \x00 \xff \xf7 \x08 \x02 \x00 \
4146+ \x00 \x00 \x00 \x00 \x00 \x00 \x00 \x00 \x00 \x10 \x00 \x00 \x00 \x2a \x34 \x64 \
4147+ \x7c \x63 \x5a \x77 \x6b \x34 \x5e \x5d \x3a \x00 ";
4148+
4149+ let hsp = HandshakePacket :: deserialize ( ( ) , & mut ParseBuf ( HSP ) ) . unwrap ( ) ;
4150+ assert_eq ! ( hsp. protocol_version( ) , 0x0a ) ;
4151+ assert_eq ! ( hsp. server_version_str( ) , "5.5.5-11.4.7-MariaDB-log" ) ;
4152+ assert_eq ! ( hsp. server_version_parsed( ) , Some ( ( 5 , 5 , 5 ) ) ) ;
4153+ assert_eq ! ( hsp. maria_db_server_version_parsed( ) , Some ( ( 11 , 4 , 7 ) ) ) ;
4154+ assert_eq ! ( hsp. connection_id( ) , 0x0b ) ;
4155+ assert_eq ! ( hsp. scramble_1_ref( ) , b"dvH@I-CJ" ) ;
4156+ assert_eq ! (
4157+ hsp. capabilities( ) ,
4158+ CapabilityFlags :: from_bits_truncate( 0xf7ff )
4159+ ) ;
4160+ assert_eq ! ( hsp. default_collation( ) , 0x08 ) ;
4161+ assert_eq ! ( hsp. status_flags( ) , StatusFlags :: from_bits_truncate( 0x0002 ) ) ;
4162+ assert_eq ! ( hsp. scramble_2_ref( ) , Some ( & b"*4d|cZwk4^]:\x00 " [ ..] ) ) ;
4163+ assert_eq ! ( hsp. auth_plugin_name_ref( ) , None ) ;
4164+ assert_eq ! (
4165+ hsp. mariadb_ext_capabilities( ) ,
4166+ MariadbCapabilities :: MARIADB_CLIENT_CACHE_METADATA
4167+ ) ;
4168+ let mut output = Vec :: new ( ) ;
4169+ hsp. serialize ( & mut output) ;
4170+ assert_eq ! ( & output, HSP ) ;
4171+ }
4172+
4173+ #[ test]
4174+ fn should_build_handshake_response_with_mariadb_capabilities ( ) {
4175+ let flags_without_db_name = CapabilityFlags :: from_bits_truncate ( 0x81aea205 ) ;
4176+ let response = HandshakeResponse :: new_mariadb (
4177+ Some ( & [ ] [ ..] ) ,
4178+ ( 5u16 , 5 , 5 ) ,
4179+ Some ( & b"root" [ ..] ) ,
4180+ None :: < & ' static [ u8 ] > ,
4181+ Some ( AuthPlugin :: MysqlNativePassword ) ,
4182+ flags_without_db_name,
4183+ None ,
4184+ 1_u32 . to_be ( ) ,
4185+ MariadbCapabilities :: MARIADB_CLIENT_CACHE_METADATA ,
4186+ ) ;
4187+ let mut actual = Vec :: new ( ) ;
4188+ response. serialize ( & mut actual) ;
4189+
4190+ let expected: Vec < u8 > = [
4191+ 0x05 , 0xa2 , 0xae , 0x81 , // client capabilities
4192+ 0x00 , 0x00 , 0x00 , 0x01 , // max packet
4193+ 0x2d , // charset
4194+ 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 ,
4195+ 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , // reserved
4196+ 0x10 , 0x00 , 0x00 , 0x00 , // mariadb capabilities
4197+ 0x72 , 0x6f , 0x6f , 0x74 , 0x00 , // username=root
4198+ 0x00 , // blank scramble
4199+ 0x6d , 0x79 , 0x73 , 0x71 , 0x6c , 0x5f , 0x6e , 0x61 , 0x74 , 0x69 , 0x76 , 0x65 , 0x5f , 0x70 ,
4200+ 0x61 , 0x73 , 0x73 , 0x77 , 0x6f , 0x72 , 0x64 , 0x00 , // mysql_native_password
4201+ ]
4202+ . to_vec ( ) ;
4203+
4204+ assert_eq ! ( expected, actual) ;
4205+ }
4206+
41384207 #[ test]
41394208 fn parse_str_to_sid ( ) {
41404209 let input = "3E11FA47-71CA-11E1-9E33-C80AA9429562:23" ;
0 commit comments