I am wondering how libevent triggers the callback. For example, let's say a client repeatedly sends a 4-byte message. In server's side, it seems not each 4-byte send will trigger a read callback. For example, I found the callback is sometimes triggered at a point of receiving 8-byte message (or other number). Is it possible to configure the libevent such that the read callback on server's side is triggered for each 4-byte message sent from the client?
Asked
Active
Viewed 914 times
1 Answers
2
I believe your problem is about sending, not about receiving. Libevent is probably not sending your data immediately because of output buffering, thus your read
callback is only invoked when the client really receives the data you've sent.
See Nagle's algorithm (aka TCP_NODELAY
). Then try disabling it to see if that's really the case:
int flag = 1;
int ret = setsockopt(sock, IPPROTO_TCP, TCP_NODELAY, &flag, sizeof(flag));
Is it possible to configure the libevent such that the read callback on server's side is triggered for each 4-byte message sent from the client?
Not really. You may receive multiple messages "simultaneously" as TCP is a stream-oriented protocol. Your application's only concern is to know where each message starts and ends.
Disregarding libevent for the purpose of explanation, you'd normally:
- Keep calling
recv
in a loop; - Append the received data/payload to a buffer;
- Invoke a method to process that buffer;
- The process method checks the buffer size to see if it contains at least 1 full message. In your case, you want it to be at least 4 bytes, so you know you have at least 1 full message to process. If your buffer has a size that's not a multiple of 4 bytes (which should never happen given the very small size of your payload), say 10 bytes, you process the initial 4 bytes, remove them from the buffer, repeat once again, and then keep the remaining 2 bytes in the buffer.

jweyrich
- 31,198
- 5
- 66
- 97
-
I see. Is it possible for server to receive a message with size not being multiple of 4? – Jes Jul 27 '15 at 21:03
-
1Keeping in mind your payload is exactly 4-byte long, then the answer is NO, but of course I don't recommend relying on this. You better use a mechanism to store received data (see [bufferevent's](http://www.wangafu.net/~nickm/libevent-book/Ref6_bufferevent.html)) and later process it. If you detect you haven't received a full message, then you should just wait for more. – jweyrich Jul 28 '15 at 01:28
-
Thank you! It makes sense this way. – Jes Jul 28 '15 at 02:08