On 12/10/2017 05:03 PM, Anastasiya Ruzhanskaya wrote:> Hello,
> I am experimenting with libvirt for my diploma. I set up an environment,
> where I can stop, resend, generate messages for libvirt.
> I am capable also standing between client and server and analyze the number
> of current procedure and decide what to do next ( I mean rpc procedure).
>
> So, for example I want to always drop creating snapshots and send an error
> to client with my custom message (NOT custom error type, but exactly custom
> message, I don't want to modify any libvirt code on client and adding
my
> errors). I am operating with bare tcp traffic, so I can easily read
> everything in the middle.
>
> So, I noticed one error for libvirt snapshots:
> 'internal error: unexpected domain snapshot snapshot1 already
exists'
> and started sending it every time I see procedure :
> REMOTE_PROC_DOMAIN_SNAPSHOT_CREATE_XML
>
> I thought, that this is possible to insert custom message here, but this is
> not true. When I change the length of the message on one symbol - it is
> still correct, on two -also , on three symbols - I get an error that the
> size of the payload is incorrect. Some other errors when I insert a message
> of random length.
>
> What is strange, that if I insert 'xxxxxxxxxxxxx...' message ,
which has
> the same length as 'internal error: unexpected domain snapshot
snapshot1
> already exists' - everything is parsed fine.
I guess when changing the error message you're not re-calculating RPC
'lengths'. For instance, at RPC level strings are encoded as follows:
| len | string .... [padding] |
Where len specifies string length, string is then whatever string
server/client is sending. At the end is optional padding so that the
whole field is aligned to multiple of 4 bytes.
Then, there's the header which contains the full length of the RPC
packet. In the code, this is calculated as the last thing, after all
other fields were placed into the packet. IOW, if you change length of a
string (or any other field) you have to recalculate the new packet
length. There's a page which describes how our RPC works:
https://libvirt.org/internals/rpc.html
BTW: A reply to call is identified by matching header fields, meaning:
program, version, procedure and serial numbers must match for client to
correctly identify reply to a call.
Michal