Weird behavior when using DoH with the multi interface

2024-06-03 Thread kartatz via curl-library

I have a simple C program where I use the CURL multi interface to download a 
bunch of files. My code looks like this:

#include 
#include 

#include 

int main(void) {
    
    int code = 0;
    size_t index = 0;
    
    int running = 1;
    CURLMsg* msg = NULL;
    int left = 0;
    
    CURL* curl = NULL;
    CURLM* curl_multi = NULL;
    
    curl = curl_easy_init();
    curl_multi = curl_multi_init();
    
    curl_easy_setopt(curl, CURLOPT_URL, "https://example.com/";);
    curl_easy_setopt(curl, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_1);
    
    curl_multi_setopt(curl_multi, CURLMOPT_MAX_HOST_CONNECTIONS, 5L);
    
    for (index = 0; index < 15; index++) {
        CURL* handle = curl_easy_duphandle(curl);
        curl_multi_add_handle(curl_multi, handle);
    }
    
    while (running) {
        curl_multi_perform(curl_multi, &running);
        
        if (running) {
            curl_multi_poll(curl_multi, NULL, 0, 1000, NULL);
        }
        
        while ((msg = curl_multi_info_read(curl_multi, &left))) {
            if (msg->msg != CURLMSG_DONE) {
                continue;
            }
            
            curl_multi_remove_handle(curl_multi, msg->easy_handle);
            
            printf("result: %i\n", (int) msg->data.result);
        }
    }
    
    return 0;
    
}

I firstly create an easy handle and then duplicate that handle with 
curl_easy_duphandle() for usage with the multi interface. For each handle, I 
set the CURLOPT_URL to the URL of the file I want to download.

I set a maximum number of host connections here (CURLMOPT_MAX_HOST_CONNECTIONS) 
because I don't want to cause overhead on the server.

This code does what I intended: download up to 5 files simultaneously.

However, things get a little weird if I set a CURLOPT_DOH_URL on the main easy 
handle:

...
curl_easy_setopt(curl, CURLOPT_DOH_URL, "https://dns.google/dns-query";);
...

This causes the multi interface to hang indefinitely. I tried setting 
CURLOPT_VERBOSE to discover what's going on, and here are the logs:

* Found bundle for host: 0xb473436429d0 [serially]
* Found bundle for host: 0xb473436429d0 [serially]
* Found bundle for host: 0xb473436429d0 [serially]
* Found bundle for host: 0xb473436429d0 [serially]
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0xb473436429d0 [serially]
* No more connections allowed to host: 5
* No connections available.

It then stays like this. No requests are performed.

After some tests, I found that setting CURLMOPT_MAX_HOST_CONNECTIONS to 
anything higher than 10 resolves this issue:

```
curl_multi_setopt(curl_multi, CURLMOPT_MAX_HOST_CONNECTIONS, 10L);
```

However, this setting causes the multi interface to make 10 requests 
simultaneously instead of just 5, which is undesired for my specific use case.

Here is the output of curl_version():

libcurl/8.7.1 OpenSSL/1.0.2k-fips zlib/1.2.7 brotli/1.0.9 libidn2/2.3.7 
libpsl/0.7.0 (+libicu/50.1.2) libssh2/1.10.0 nghttp2/1.33.0 OpenLDAP/2.4.44

I'm on CentOS 7.
-- 
Unsubscribe: https://lists.haxx.se/mailman/listinfo/curl-library
Etiquette:   https://curl.se/mail/etiquette.html


Re: Weird behavior when using DoH with the multi interface

2024-06-04 Thread kartatz via curl-library

 On Tue, 4 Jun 2024, Daniel Stenberg via curl-library wrote:

> Interesting case. I think we should make DoH requests exempt from that
> check/restriciton, as otherwise you can end up in this kind of catch-22
> situation.

kartatz, how about a patch like this?
 Thank you for the patch!

I checked out the latest master from GitHub and did a minimal curl build with 
CMake (-DHTTP_ONLY=ON) using OpenSSL as SSL backend.

Now the multi interface can resolve using DoH, but the program crashes as soon 
as it attempts to connect to the resolved address:

* Found bundle for host: 0x119dc60 [serially]
* Found bundle for host: 0x119dc60 [serially]
* Found bundle for host: 0x119dc60 [serially]
* Found bundle for host: 0x119dc60 [serially]
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Found bundle for host: 0x119dc60 [serially]
* No more connections allowed to host: 5
* No connections available.
* Host example.com:443 was resolved.
* IPv6: 2606:2800:21f:cb07:6820:80da:af6b:8b2c
* IPv4: 93.184.215.14
*   Trying 93.184.215.14:443...
* Hostname 'example.com' was found in DNS cache
[1]    15690 segmentation fault  ./main

I attached the gdb logs.

 
Starting program: /home/kartz/main 
Missing separate debuginfos, use: debuginfo-install glibc-2.17-326.el7_9.x86_64
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib64/libthread_db.so.1".

Program received signal SIGSEGV, Segmentation fault.
0x77f5bb19 in start_connect (cf=0x457b50, 
data=0x42a9d0, remotehost=0x0)
    at /home/kartz/curl/lib/connect.c:780
780 ai_family0 = remotehost->addr?
Missing separate debuginfos, use: debuginfo-install 
keyutils-libs-1.5.8-3.el7.x86_64 krb5-libs-1.15.1-55.el7_9.x86_64 
libcom_err-1.42.9-19.el7.x86_64 libselinux-2.5-15.el7.x86_64 
openssl-libs-1.0.2k-26.el7_9.x86_64 pcre-8.32-17.el7.x86_64 
zlib-1.2.7-21.el7_9.x86_64
#0  0x77f5bb19 in start_connect (cf=0x457b50, 

data=0x42a9d0, remotehost=0x0)
    at /home/kartz/curl/lib/connect.c:780
ctx = 0x453320
conn = 0x43f770
result = CURLE_COULDNT_CONNECT
ai_family0 = 0
ai_family1 = 0
timeout_ms = 294872
addr0 = 0x3004012f0
addr1 = 0x77f5c79b 
<cf_happy_eyeballs_create+149>
#1  0x77f5c000 in cf_he_connect (cf=0x457b50, 

data=0x42a9d0, blocking=false, 
done=0x7fffdb8f)
    at /home/kartz/curl/lib/connect.c:898
ctx = 0x453320
result = CURLE_OK
#2  0x77f57f79 in Curl_conn_cf_connect[

Re: Weird behavior when using DoH with the multi interface

2024-06-04 Thread kartatz via curl-library


I don't think my patch causes that. The PR ran 159 successful CI jobs.

Yes, you are right.

It appears that something from my previous builds was messing with things. I 
deleted the build directory and did a clean build. This time, everything worked 
as expected.

I apologize for not checking properly.
-- 
Unsubscribe: https://lists.haxx.se/mailman/listinfo/curl-library
Etiquette:   https://curl.se/mail/etiquette.html