Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Possible busy-looping in curl_multi_poll #4594

Closed
3dyd opened this issue Nov 14, 2019 · 3 comments
Assignees

Comments

@3dyd
Copy link
Contributor

@3dyd 3dyd commented Nov 14, 2019

Take a look at this piece of code at the end of Curl_multi_wait:

curl/lib/multi.c

Lines 1150 to 1161 in 7a46aeb

if(!extrawait || extra_fds || curlfds)
/* if any socket was checked */
;
else {
long sleep_ms = 0;
/* Avoid busy-looping when there's nothing particular to wait for */
if(!curl_multi_timeout(multi, &sleep_ms) && sleep_ms) {
if(sleep_ms > timeout_ms)
sleep_ms = timeout_ms;
Curl_wait_ms((int)sleep_ms);
}

If curl_multi_poll is given valid empty multi handle (no easy handles were added to it [yet]) without extra curl_waitfd structures then sleep_ms receives value -1 from curl_multi_timeout effectively avoiding waiting for given timeout_ms period. So function returns immediately.

Is this intended behavior, and such edge case still has to be accounted by the caller to avoid busy-looping?

@bagder bagder self-assigned this Nov 14, 2019
@bagder

This comment has been minimized.

Copy link
Member

@bagder bagder commented Nov 14, 2019

I think it should wait for the timeout period in this case. Something like this?

diff --git a/lib/multi.c b/lib/multi.c
index 7e8e38dc9..db08ac636 100755
--- a/lib/multi.c
+++ b/lib/multi.c
@@ -1155,10 +1155,12 @@ static CURLMcode Curl_multi_wait(struct Curl_multi *multi,
 
     /* Avoid busy-looping when there's nothing particular to wait for */
     if(!curl_multi_timeout(multi, &sleep_ms) && sleep_ms) {
       if(sleep_ms > timeout_ms)
         sleep_ms = timeout_ms;
+      else if((sleep_ms < 0) && extrawait)
+        sleep_ms = timeout_ms;
       Curl_wait_ms((int)sleep_ms);
     }
   }
 
   return CURLM_OK;
bagder added a commit that referenced this issue Nov 14, 2019
Fixes #4594
Reported-by: 3dyd on github
@3dyd

This comment has been minimized.

Copy link
Contributor Author

@3dyd 3dyd commented Nov 14, 2019

Not sure if notification is fired if one comments diff directly, so I am duplicating it here:

else if((sleep_ms < 0) && extrawait)

extrawait is always true in this block.

@3dyd

This comment has been minimized.

Copy link
Contributor Author

@3dyd 3dyd commented Nov 14, 2019

Confirmed the change has fixed described issue.

@bagder bagder closed this in 4e1eee1 Nov 14, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
2 participants
You can’t perform that action at this time.