[ 
https://issues.apache.org/jira/browse/PROTON-2104?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=17252176#comment-17252176
 ] 

Jiri Daněk commented on PROTON-2104:
------------------------------------

The class proton::url handles IPv6 addresses in the format {{[ip]:port}} just 
fine. The problem is when the C++ binding hands this to the C proactor.

First, {{proton::container::impl::start_connection}} calls 
{{pn_proactor_addr}}, which transforms the original {{[ip]:port}} into 
{{ip:port}}, thus irrecoverably destroying the IPv6 address structure.

{code}
void container::impl::start_connection(const url& url, pn_connection_t *pnc) {
    pn_transport_t* pnt = pn_transport();
    connection_context& cc = connection_context::get(pnc);
    connection_options& co = *cc.connection_options_;
    co.apply_unbound_client(pnt);

    char caddr[PN_MAX_ADDR];
    pn_proactor_addr(caddr, sizeof(caddr), url.host().c_str(), 
url.port().c_str());
    pn_proactor_connect2(proactor_, pnc, pnt, caddr); // Takes ownership of 
pnc, pnt
}
{code}

{code}
int pn_proactor_addr(char *buf, size_t len, const char *host, const char *port) 
{
  return snprintf(buf, len, "%s:%s", host ? host : "", port ? port : "");
}
{code}

Next, {{pni_parse_addr}} (called from {{pn_proactor_connect2}}) is unable to 
parse an IPv6 address, even if it was formatted correctly by the previous step

{code}
int pni_parse_addr(const char *addr, char *buf, size_t len, const char **host, 
const char **port)
{
  size_t hplen = strlen(addr);
  if (hplen >= len) {
    return PN_OVERFLOW;
  }
  memcpy(buf, addr, hplen+1);
  char *p = strrchr(buf, ':');
  if (p) {
    *port = p + 1;
    *p = '\0';
    if (**port == '\0' || !strcmp(*port, AMQP_PORT_NAME)) {
      *port = AMQP_PORT;
    } else if (!strcmp(*port, AMQPS_PORT_NAME)) {
      *port = AMQPS_PORT;
    }
  } else {
    *port = AMQP_PORT;
  }
  if (*buf) {
    *host = buf;
  } else {
    *host = NULL;
  }
  return 0;
}
{code}

This investigation suggests that the {{send}} c example is unlikely to fare 
better, when given an IPv6 address. And that looks to be the case.

{noformat}
% cmake-build-debug/c/examples/send 'fe80::c662:ab36:1ef1:1596' '5672' 'abc'
PN_TRANSPORT_CLOSED: proton:io: Invalid argument - on connect 
fe80::c662:ab36:1ef1:1596:5672
{noformat}

> [c++ client] Error specifying url with IPv6 literal host address
> ----------------------------------------------------------------
>
>                 Key: PROTON-2104
>                 URL: https://issues.apache.org/jira/browse/PROTON-2104
>             Project: Qpid Proton
>          Issue Type: Bug
>          Components: cpp-binding
>    Affects Versions: proton-c-0.29.0
>            Reporter: Charles E. Rolke
>            Priority: Major
>
> C++ examples simple_send and simple_recv accept IPv6 loopback address [::1] 
> but have issues with other apparently legal addresses.
> These work on my system:
> {noformat}
> ping6 fe80::c662:ab36:1ef1:1596
> ping6 fe80::c662:ab36:1ef1:1596%wlp4s0
> ping6 fe80:0000:0000:0000:c662:ab36:1ef1:1596
> {noformat}
> Wrapping the host part in square brackets and sending that address to 
> simple_send fails:
> {noformat}
>  ./simple_send -a [fe80::c662:ab36:1ef1:1596]:5672/abc
>  proton:io: Invalid argument - on connect fe80::c662:ab36:1ef1:1596:5672
> {noformat}
> All three variants of the address that work with ping6 fail with the same 
> error on the simple_send command line.
>  



--
This message was sent by Atlassian Jira
(v8.3.4#803005)

---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to