Monday, 17 October 2022

Deserializing gRPC message

Problem

I intercepted a gRPC network request from an application, and I intend to modify the contents and resend the message programmatically. As no tools (except for MitmProxy, see below) were able to decode the protobuf data I wanted to know why that is.

The gRPC payload sent from the client:

gRPC header       | Protobuf data
[00] [00 00 00 22] [12 12 09 c3 8d 09 16 c3 93 2a c2 a5 4d 40 11 14 39 c3 ab 6b c2 a2 c3 b3 31 40 1a 05 65 6e 2d 53 45 1a 05 73 76 2d 53 45]
 ^^       ^^ Payload length
Compressed flag

What I've tried

Failure

  • protoc --decode_raw on the protobuf data, but I get Failed to parse input.
  • CyberChef with protobuf decode, gives Error: Exhausted Buffer
  • The blackboxprotobuf python module, raising google.protobuf.message.DecodeError: Invalid Message Length

Success

MitmProxy was able to decode the data to the following:

gRPC message 0 (compressed False)
[message]    2
[fixed64]    2.1   4633543028839346763
[fixed64]    2.2   4625748902140211098
[message]    3
[fixed32]    3.12  1163079022
[string]     3     sv-SE

Manually decoding

[message]
00010 010 00010010
  2   LEN    18

[fixed64]
00001 001 [11000011 10001101 00001001 00010110 11000011 10010011 00101010 11000010]
  1   I64                            13991157658477498000

[fixed32]
10100 101 [01001101 01000000 00010001 00010100]
  20  I32              336674893

[fixed64]
00111 001 [11000011 10101011 01101011 11000010 10100010 11000011 10110011 00110001]
  7   I64                            3581421232503631000

[unknown]
01000 000 [00011010 00000101]
  8  VARINT       ???

[message]
00011 010 00000101 
  3   LEN    5

[fixed32]
01100 101 [01101110 00101101 01010011 01000101]
 12   I32              1163079022

[string]
00011 010 00000101 [01110011 01110110 00101101 01010011 01000101]
  3   LEN    7         s         v       -        S         E

I decoded it using the google documentation as reference: https://developers.google.com/protocol-buffers/docs/encoding. However, I am not familiar with gRPC or protobuf so I have likely have gaps in my knowledge.

Worth noting:

  • I was able to successfully decode all server responses without problems.
  • The payload length as indicated by the gRPC header (0x22) differs from its actual length (0x28).
  • MitmProxy has access to both the gRPC headers and the protobuf data, while the other tools I tried (that all failed) only support protobuf data as input.
  • I do not know for a fact that MitmProxy decoded the data correctly, only that it ran without exceptions
  • According to the user agent, the client uses grpc-swift-nio/1.9.0


from Deserializing gRPC message

No comments:

Post a Comment