@@ -34,64 +34,24 @@ pub fn encode_var_int32(
3434/// Decode VarInt32 (signed 32-bit variable-length integer)
3535///
3636/// Decodes from the specified position in the byte array, returns (decoded value, bytes consumed)
37+ /// Note: Negative numbers are encoded using VarInt64 format (10 bytes), so we use decode_var_int64
38+ /// and then check the range
3739pub fn decode_var_int32 (
3840 bytes : & [ u8 ] ,
3941 offset : usize ,
4042) -> Result < ( i32 , usize ) , Box < dyn std:: error:: Error + Send > > {
41- let mut value: i32 = 0 ;
42- let mut shift = 0 ;
43- let mut pos = offset;
44-
45- loop {
46- if pos >= bytes. len ( ) {
47- return Err ( Box :: new ( std:: io:: Error :: new (
48- std:: io:: ErrorKind :: UnexpectedEof ,
49- "Incomplete VarInt32" ,
50- ) ) ) ;
51- }
52-
53- let b = bytes[ pos] as i8 ;
54- pos += 1 ;
55-
56- if b >= 0 {
57- value |= ( b as i32 ) << shift;
58- return Ok ( ( value, pos - offset) ) ;
59- }
60-
61- value |= ( ( b as i32 ) ^ ( 0xffffff80u32 as i32 ) ) << shift;
62- shift += 7 ;
63-
64- if shift >= 35 {
65- // Handle negative numbers, need to read additional bytes
66- if pos >= bytes. len ( ) || bytes[ pos] != 0xff {
67- return Err ( Box :: new ( std:: io:: Error :: new (
68- std:: io:: ErrorKind :: InvalidData ,
69- "Invalid VarInt32 encoding" ,
70- ) ) ) ;
71- }
72- pos += 1 ;
73-
74- for _ in 0 ..4 {
75- if pos >= bytes. len ( ) || bytes[ pos] != 0xff {
76- return Err ( Box :: new ( std:: io:: Error :: new (
77- std:: io:: ErrorKind :: InvalidData ,
78- "Invalid VarInt32 encoding" ,
79- ) ) ) ;
80- }
81- pos += 1 ;
82- }
83-
84- if pos >= bytes. len ( ) || bytes[ pos] != 0x01 {
85- return Err ( Box :: new ( std:: io:: Error :: new (
86- std:: io:: ErrorKind :: InvalidData ,
87- "Invalid VarInt32 encoding" ,
88- ) ) ) ;
89- }
90- pos += 1 ;
91-
92- return Ok ( ( value, pos - offset) ) ;
93- }
43+ // Since encode_var_int32 uses encode_var_int64 for negative numbers,
44+ // we need to use decode_var_int64 and then check the range
45+ let ( decoded, consumed) = decode_var_int64 ( bytes, offset) ?;
46+
47+ if decoded < i32:: MIN as i64 || decoded > i32:: MAX as i64 {
48+ return Err ( Box :: new ( std:: io:: Error :: new (
49+ std:: io:: ErrorKind :: InvalidData ,
50+ "VarInt32 value out of range" ,
51+ ) ) ) ;
9452 }
53+
54+ Ok ( ( decoded as i32 , consumed) )
9555}
9656
9757/// Encode VarUInt32 (unsigned 32-bit variable-length integer)
0 commit comments