windows socket ipv6 SOCK_RAW

bind处一直报错WSAEADDRNOTAVAIL10049,不知道为什么?

WSAEADDRNOTAVAIL 10049
Cannot assign requested address.
The requested address is not valid in its context. This normally results from an attempt to bind to an address that is not valid for the local computer. This can also result from connect, sendto, WSAConnect, WSAJoinLeaf, or WSASendTo when the remote address or port is not valid for a remote computer (for example, address or port 0).

 win10, vs2015

#include <stdio.h>
#include <winsock2.h>
#include <ws2ipdef.h>

#pragma comment(lib, "ws2_32.lib")

#define BUF_SIZE 30

int main()
{
    int iResult = 0;
    WSADATA wsaData;
    SOCKET sock;
    char message[BUF_SIZE];
    int strlen;
    int addrsize;

    SOCKADDR_IN6 addrto, addrfrom;

    iResult = WSAStartup(MAKEWORD(2, 2), &wsaData);

    sock = socket(AF_INET6, SOCK_RAW, 89);    /*需要管理员权限*/
    if (sock == INVALID_SOCKET)
        printf("sock err = %d\n", WSAGetLastError());

    addrto.sin6_family = AF_INET6;
    addrto.sin6_addr.u.Byte[0] = 0xfc; 
    addrto.sin6_addr.u.Byte[1] = 0x00;
    addrto.sin6_addr.u.Byte[2] = 0x00;
    addrto.sin6_addr.u.Byte[3] = 0x00;
    addrto.sin6_addr.u.Byte[4] = 0x00;
    addrto.sin6_addr.u.Byte[5] = 0x00;
    addrto.sin6_addr.u.Byte[6] = 0x0d;
    addrto.sin6_addr.u.Byte[7] = 0x41;
    addrto.sin6_addr.u.Byte[8] = 0x00;
    addrto.sin6_addr.u.Byte[9] = 0x00;
    addrto.sin6_addr.u.Byte[10] = 0x00;
    addrto.sin6_addr.u.Byte[11] = 0x00;
    addrto.sin6_addr.u.Byte[12] = 0x0d;
    addrto.sin6_addr.u.Byte[13] = 0x41;
    addrto.sin6_addr.u.Byte[14] = 0x00;
    addrto.sin6_addr.u.Byte[15] = 0x02;
    addrto.sin6_port = 89;

    iResult = bind(sock, (SOCKADDR *)&addrto, sizeof(SOCKADDR_IN6));
    if (iResult == SOCKET_ERROR)
        printf("bind err = %d\n", WSAGetLastError());

    while (1)
    {
        addrsize = sizeof(addrfrom);
        strlen = recvfrom(sock, message, BUF_SIZE, 0, (SOCKADDR*)&addrfrom, &addrsize);
    }

}

 

IPv4版本,需要保证本地连接已接通

#define _WINSOCK_DEPRECATED_NO_WARNINGS
#include <stdio.h>
#include <winsock2.h>
#include <ws2ipdef.h>
#include <ws2tcpip.h>

#pragma comment(lib, "ws2_32.lib")

#define BUF_SIZE 30
#define _WINSOCK_DEPRECATED_NO_WARNINGS

int main()
{
    int iResult = 0;
    WSADATA wsaData;
    SOCKET sock;
    char message[BUF_SIZE] = "send...";
    int strlen;
    int addrsize;

    SOCKADDR_IN addrto, addrfrom;

    iResult = WSAStartup(MAKEWORD(2, 2), &wsaData);

    sock = socket(AF_INET, SOCK_RAW, 89);    /*需要管理员权限*/
    if (sock == INVALID_SOCKET)
        printf("sock err = %d\n", WSAGetLastError());

    addrfrom.sin_family = AF_INET;
    addrfrom.sin_addr.S_un.S_addr = inet_addr("192.168.0.4");
    addrfrom.sin_port = 89;

    addrto.sin_family = AF_INET;
    addrto.sin_addr.S_un.S_addr = inet_addr("192.168.0.5");
    addrto.sin_port = 89;

    iResult = bind(sock, (SOCKADDR *)&addrfrom, sizeof(addrfrom));
    if (iResult == SOCKET_ERROR)
        printf("bind err = %d\n", WSAGetLastError());

    while (1)
    {
        addrsize = sizeof(addrto);
        strlen = sendto(sock, message, BUF_SIZE, 0, (SOCKADDR*)&addrto, addrsize);
    }

}

 IPv6版本,2000::2可以通,addrfrom.sin6_scope_id = 0;地址范围设置是必须的,若为unicast地址可以设置为0。需要赋值,不然内存默认可能为cc。

#define _WINSOCK_DEPRECATED_NO_WARNINGS
#include <stdio.h>
#include <winsock2.h>
#include <ws2ipdef.h>
#include <ws2tcpip.h>
#include <wsipv6ok.h>

#pragma comment(lib, "ws2_32.lib")

#define BUF_SIZE 30
#define _WINSOCK_DEPRECATED_NO_WARNINGS

int main()
{
    int iResult = 0;
    WSADATA wsaData;
    SOCKET sock;
    char message[BUF_SIZE] = "send...";
    int strlen;
    int addrsize;
    SOCKADDR_IN6 addrto, addrfrom;

    iResult = WSAStartup(MAKEWORD(2, 2), &wsaData);

    sock = socket(AF_INET6, SOCK_RAW, 89);    /*需要管理员权限*/
    if (sock == INVALID_SOCKET)
        printf("sock err = %d\n", WSAGetLastError());

    addrfrom.sin6_family = AF_INET6;
    iResult = inet_pton(AF_INET6, "2000::2", addrfrom.sin6_addr.u.Byte);
    addrfrom.sin6_port = htons(89);
    addrfrom.sin6_scope_id = 0;

    addrto.sin6_family = AF_INET6;
    iResult = inet_pton(AF_INET6, "2000::1", addrto.sin6_addr.u.Byte);
    addrto.sin6_port = htons(89);
    addrto.sin6_scope_id = 0;

    iResult = bind(sock, (SOCKADDR *)&addrfrom, sizeof(addrfrom));
    if (iResult == SOCKET_ERROR)
        printf("bind err = %d\n", WSAGetLastError());

    while (1)
    {
        addrsize = sizeof(addrto);
        strlen = sendto(sock, message, BUF_SIZE, 0, (SOCKADDR*)&addrto, addrsize);
        printf("sendto err = %d\n", WSAGetLastError());
    }

}

 IPv6通,主要是scope_id

#define _WINSOCK_DEPRECATED_NO_WARNINGS
#include <stdio.h>
#include <winsock2.h>
#include <ws2ipdef.h>
#include <ws2tcpip.h>
#include <wsipv6ok.h>

#pragma comment(lib, "ws2_32.lib")

#define BUF_SIZE 30
#define _WINSOCK_DEPRECATED_NO_WARNINGS

int main()
{
    int iResult = 0;
    WSADATA wsaData;
    SOCKET sock;
    char message[BUF_SIZE] = "send...";
    int strlen;
    int addrsize;
    SOCKADDR_IN6 addrto, addrfrom;

    iResult = WSAStartup(MAKEWORD(2, 2), &wsaData);

    sock = socket(AF_INET6, SOCK_RAW, 89);    /*需要管理员权限*/
    if (sock == INVALID_SOCKET)
        printf("sock err = %d\n", WSAGetLastError());

    addrfrom.sin6_family = AF_INET6;
    iResult = inet_pton(AF_INET6, "fc00::d41:0:0:d41:2", addrfrom.sin6_addr.u.Byte);
    addrfrom.sin6_port = htons(89);
    addrfrom.sin6_scope_id = 0;

    addrto.sin6_family = AF_INET6;
    iResult = inet_pton(AF_INET6, "fc00::d41:0:0:d41:1", addrto.sin6_addr.u.Byte);
    addrto.sin6_port = htons(89);
    addrto.sin6_scope_id = 0;

    iResult = bind(sock, (SOCKADDR *)&addrfrom, sizeof(addrfrom));
    if (iResult == SOCKET_ERROR)
        printf("bind err = %d\n", WSAGetLastError());

    while (1)
    {
        addrsize = sizeof(addrto);
        strlen = sendto(sock, message, BUF_SIZE, 0, (SOCKADDR*)&addrto, addrsize);
        printf("sendto err = %d\n", WSAGetLastError());
    }

}

 

 

转载于:https://www.cnblogs.com/yanhc/p/10306304.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值