Let's assume there are two interfaces:
eth0: ipv4 AND ipv6: 1.1.1.1 / 2001:.....
eth1: only ipv4: 2.2.2.2
curl --interface 2.2.2.2 <host>
fails when <host> has both ipv6 and ipv4 adresses:
curl: (45) bind failed with errno 22: Invalid argument
To prevent that, one has to manually specify --ipv4 / -4,
In my opinion this should be implied, since we are binding to an ipv4-only interface and it makes no sense preferring ipv6 over ipv4.
You didn't state what version or OS you use.
The idea is however that the resolved IP is what dictates what interface/address to bind the local end to. Can you please try the current git/tomorrow's daily snapshot and see how it works?
If it still fails, can you please A) show us the full -v output and B) show use the "curl -V" output.
I'm on debian/lenny
curl without c-ares:
$ ./curl -V
curl 7.21.3-DEV (i686-pc-linux-gnu) libcurl/7.21.3-DEV OpenSSL/0.9.8g zlib/1.2.3.3 libidn/1.8 libssh2/0.18
Protocols: dict file ftp ftps gopher http https imap imaps ldap ldaps pop3 pop3s rtsp scp sftp smtp smtps telnet tftp
Features: IDN IPv6 Largefile NTLM SSL libz
$ ./curl --interface XX.XX.XX.XX www.google.com -v
* About to connect() to www.google.com port 80 (#0)
* Trying 2a00:1450:8001::63... getaddrinfo(3) failed for XX.XX.XX.XX:0
* Couldn't bind to 'XX.XX.XX.XX'
* Closing connection #0
curl: (45) Couldn't bind to 'XX.XX.XX.XX'
curl with c-ares:
$ ./curl -V
curl 7.21.3-DEV (i686-pc-linux-gnu) libcurl/7.21.3-DEV OpenSSL/0.9.8g zlib/1.2.3.3 c-ares/1.7.3 libidn/1.8 libssh2/0.18
Protocols: dict file ftp ftps gopher http https imap imaps ldap ldaps pop3 pop3s rtsp scp sftp smtp smtps telnet tftp
Features: AsynchDNS IDN IPv6 Largefile NTLM SSL libz
$ ./curl --interface XX.XX.XX.XX www.google.com -v
* About to connect() to www.google.com port 80 (#0)
* Trying 2a00:1450:8001::63... Name 'XX.XX.XX.XX' family 10 resolved to 'XX.XX.XX.XX' family 2
* bind failed with errno 22: Invalid argument
* Closing connection #0
curl: (45) bind failed with errno 22: Invalid argument
Adding --ipv4 to curl's commandline works just fine in both cases.
I'm just wondering why it tries ipv6 in the first place, when the --interface specified is ipv4-only.
The answer to why:
curl resolves the target host first and uses the preferred IP version there. Then it binds the local end and it then tries to do that using the same IP version that it resolved the host name with...
Due the nature of this, this request is on the border to a feature request. I'm setting this bug entry as 'later' in the hope that we will get a better approach to this problem in the future. As there's nobody working on this now and I don't know of anyone with plans for it, I don't want this lingering around.
Thanks anyway for bring this to our attention.
Looks like this is fixed in recent curl versions.
I guess this commit did it: 090b55c100be4364ac035b5a1b7440cf94e71904 / bug 1189