连接到 IPv4 映射的 IPv6 地址失败

标签 c linux sockets ipv6

我正在尝试在 Linux (debian-lenny-64 2.6.26-2-amd64) 上使用 IPv6 套接字连接到使用 IPv4 映射 IPv6 地址的 IPv4 地址

#include <sys/types.h>
#include <sys/socket.h>
#include <netdb.h>
#include <errno.h>
#include <stdlib.h>
#include <stdio.h>

int main(int argc, void **argv)
{
    struct addrinfo *sa;
    struct addrinfo *ra;

    int err = getaddrinfo("2001:DB8::2", 0, 0, &sa);

    int fd = socket(sa->ai_family, SOCK_DGRAM, 0);

    int v6only = 0;     

    err = setsockopt(fd, IPPROTO_IPV6, IPV6_V6ONLY, (void *)&v6only, sizeof(v6only)); 

    err = bind(fd, sa->ai_addr, sa->ai_addrlen);

    err = getaddrinfo("::ffff:192.168.0.1", "9", 0, &ra);

//  err = getaddrinfo("2001:DB8::1", "9", 0, &ra);
//  err = getaddrinfo("::ffff:127.0.0.1", "9", 0, &ra);

    err = connect(fd, (struct sockaddr *)ra->ai_addr, sizeof(struct sockaddr_in6));
}

(我已经从粘贴的代码中删除了错误测试)

2001:DB8::2 和 192.168.0.2 是本地地址(都在同一接口(interface)上)。
2001:DB8::1 和 192.168.0.1 是远程地址(都在同一接口(interface)上)。

我更改了连接调用的远程地址并得到以下信息:

  • 连接到::ffff:127.0.0.1 成功(本地主机)
  • 连接到 2001:DB8::1 成功(远程 IPv6 地址)
  • 连接到::ffff:192.168.0.2成功(本地IPv4地址)
  • 连接到::ffff:192.168.0.1 失败(22 无效参数 - 远程 IPv4)

如果我更改为进行 IPv4 连接,那么连接也可以正常工作。

我认为某处的路由一定有问题,但我不知道我需要更改什么。 首先,理论上我应该能够做到这一点吗?
知道出了什么问题吗?

最佳答案

  • 查看函数“getaddrinfo()”为
     ~$ man getaddrinfo 
    .
  • 函数的“hints”参数具有属性“ai_flags”,如果您将其设置为“AI_PASSIVE”。它适用于 IPv4 和 IPv6 寻址模式。

关于连接到 IPv4 映射的 IPv6 地址失败,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9892770/

相关文章:

c - 如何通过 gatt 从 esp32 的 hid ble 键盘发送扫描代码 >255?

我们可以在 C 语言中将整数值转换为指针类型吗?

c - 从服务器向客户端发送消息

c++ - 读取和写入套接字

c - sqlite 中的执行起点

c - 我无法执行在 else if 语句中包含用户输入的整数的程序

linux - mongodb 无法从 mongo.conf 开始

linux - 如何找到 centOS 7 上安装了 binutils 的位置?

c - 在多线程服务器程序中使用 linux 信号处理程序实现每 25 毫秒执行一次浮点计算的程序?

ios - iOS Swift : How to check if port is open