Skip to content
This repository was archived by the owner on May 4, 2018. It is now read-only.

Make uv_udp_send send data immediately if possible - #1358

Merged
saghul merged 2 commits into
joyent:masterfrom
saghul:udp-send-immediate
Jul 8, 2014
Merged

Make uv_udp_send send data immediately if possible#1358
saghul merged 2 commits into
joyent:masterfrom
saghul:udp-send-immediate

Conversation

@saghul

@saghul saghul commented Jul 5, 2014

Copy link
Copy Markdown
Contributor

Please review with care.

/cc @indutny @txdv @ibc

Comment thread src/unix/udp.c Outdated

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You mean send_queue_size.

@ibc

ibc commented Jul 5, 2014

Copy link
Copy Markdown

Please yes. UDP is important, really. Not so much as TCP (and its loved HTTP which dominates the world and will replace "Internet") but, somehow, UDP may be important.

@saghul

saghul commented Jul 6, 2014

Copy link
Copy Markdown
Contributor Author

Thanks for the comments, @ibc. I wanted to put it up for review quickly in case you guys had some spare cycles to review the code.

Now, this patchset includes some required minor changes to how UDP handles operate internally, which actually make them a bit more similar to how streams behave:

  • When @txdv introduced the send_queue_size/count, it was decreased the moment sendmsg happened. It's now deferred until the request is popped out of the completed queue, right before the callback is called. The reson for this is that if you call uv_udp_send and the send completes immediately, uv_try_send would also try to send a datagram, and succeed, before the send callback from the previous send request was ever called, thus creating some inconsistent situations. Moreover, it's important not to decrease the byte count in case of error, because the user could think that the write completed ok (before getting the callback) because the size is 0, and continue attempting to write on a dead UDP handle. (this is also the case for streams, btw).

An interesting note: the change I had to make in test-watcher-cross-stop ilustrates the usefulness of this patch. On Linux, all send requests are completed immediately, on that test.

@saghul

saghul commented Jul 6, 2014

Copy link
Copy Markdown
Contributor Author

Please yes. UDP is important, really. Not so much as TCP (and its loved HTTP which dominates the world and will replace "Internet") but, somehow, UDP may be important.

Nobody said otherwise. Features are developed if/when there is need, curiosity, interest or patches, but there is only so much time. Discussions and patches like what @txdv you and I have done for try_send really motivate me to improve UDP, so here we are :-)

@txdv

txdv commented Jul 6, 2014

Copy link
Copy Markdown

I'm reviewing wait a bit.

@saghul

saghul commented Jul 6, 2014

Copy link
Copy Markdown
Contributor Author

I'm reviewing wait a bit.

Thanks! No rush, we are not in a hurry.

@saghul

saghul commented Jul 6, 2014

Copy link
Copy Markdown
Contributor Author

@txdv force pushed. Now all the requests that will never complete are added to que completed queue and run in order. This actually makes the code more concise, as there is a single place where the completed queue is processed, req-> status will have the correct value (ECANCELLED), and I added a couple of asserts about queue_size/count, since they should be 0 after all callbacks have been run.

@txdv

txdv commented Jul 6, 2014

Copy link
Copy Markdown

More delitions than additions and a feature more.

One central place to call the the send_cb makes it more concise, yes.

One question though, why are we calling the send_cb on success with 0 though?

https://github.com/saghul/libuv/blob/a29ea0fd5f34c9e8ebfd51a2363e57ff6ffb3f38/src/unix/udp.c#L112-L114

Don't we want to pass the amount we have written?

@saghul

saghul commented Jul 6, 2014

Copy link
Copy Markdown
Contributor Author

Don't we want to pass the amount we have written?

I didn't change that. I guess the reason is that in UDP you either send the whole datagram or you don't. But we could get rid of the if and always return req->status, which has the number of bytes written.

@saghul

saghul commented Jul 6, 2014

Copy link
Copy Markdown
Contributor Author

5 tests are failing

Hum, I cannot reproduce that on my Linux machine. I'll go through the code and test it on OSX as well a bit later.

@txdv

txdv commented Jul 6, 2014

Copy link
Copy Markdown

@saghul It was my changed that made it fail, It is not failing.

Node used to return the buffer.length (which was faulty, because we could send less).

nodejs/node-v0.x-archive@a382c9a97 look at dgram.js

Now it returns the sent size. Maybe we should get rid of the if in libuv and just pass status.

It would be 'consistent' with the write function I guess? Do stream_write cbs get a callback with 0 or the size of what they have written?

@saghul

saghul commented Jul 6, 2014

Copy link
Copy Markdown
Contributor Author

@txdv they get 0, because the callback is not called until all data has been sent. So it's already consistent. I could update the comment, though.

@txdv

txdv commented Jul 6, 2014

Copy link
Copy Markdown

Does the uv_write_cb in uv_write get called with 0 as well?

@saghul

saghul commented Jul 6, 2014

Copy link
Copy Markdown
Contributor Author

Does the uv_write_cb in uv_write get called with 0 as well?

Yes.

@saghul

saghul commented Jul 6, 2014

Copy link
Copy Markdown
Contributor Author

@indutny, this one is ready to land IMHO, can you PTAL?

@saghul

saghul commented Jul 6, 2014

Copy link
Copy Markdown
Contributor Author

I already merged the last patch I had in this set (377bf68). It was unrelated and almost all UDP tests were failing on Windows without it.

@txdv

txdv commented Jul 6, 2014

Copy link
Copy Markdown

yes, my mistake, should have been in my commit

@saghul

saghul commented Jul 6, 2014

Copy link
Copy Markdown
Contributor Author

No problem!

@saghul

saghul commented Jul 7, 2014

Copy link
Copy Markdown
Contributor Author

@indutny, any further comments?

saghul added 2 commits July 8, 2014 18:44
It's possible that recv_cb_called is bigger than the number of sockets,
because if all sends succeed the recv callback is called twice: once
with the actual data, and another time with 0.
@saghul
saghul merged commit ad78e45 into joyent:master Jul 8, 2014
@saghul

saghul commented Jul 8, 2014

Copy link
Copy Markdown
Contributor Author

Thanks guys, landed!

@saghul
saghul deleted the udp-send-immediate branch September 11, 2014 19:52
yosuke-furukawa added a commit to nodejs/node that referenced this pull request May 10, 2015
dgram#send callback was changed synchronously.
The PR-URL is here joyent/libuv#1358

This commit is temporary fix until libuv issue is resolved.
libuv/libuv#301

PR-URL: #1313
Reviewed-By: Ben Noordhuis <info@bnoordhuis.nl>
Reviewed-By: Trevor Norris <trev.norris@gmail.com>
Fishrock123 pushed a commit to Fishrock123/node that referenced this pull request May 19, 2015
dgram#send callback was changed synchronously.
The PR-URL is here joyent/libuv#1358

This commit is temporary fix until libuv issue is resolved.
libuv/libuv#301

PR-URL: nodejs#1313
Reviewed-By: Ben Noordhuis <info@bnoordhuis.nl>
Reviewed-By: Trevor Norris <trev.norris@gmail.com>
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants