sendto 関数 (winsock.h)

sendto 関数は、特定の宛先にデータを送信します。

構文

int sendto(
  [in] SOCKET         s,
  [in] const char     *buf,
  [in] int            len,
  [in] int            flags,
  [in] const sockaddr *to,
  [in] int            tolen
);

パラメーター

[in] s

(接続されている可能性がある) ソケットを識別する記述子。

[in] buf

送信するデータを含むバッファーへのポインター。

[in] len

buf パラメーターが指すデータの長さ (バイト単位)。

[in] flags

呼び出しの方法を指定するフラグのセット。

[in] to

ターゲット ソケットのアドレスを含む sockaddr 構造体への省略可能なポインター。

[in] tolen

to パラメーターが指すアドレスのサイズ (バイト単位)。

戻り値

エラーが発生しない場合、 sendto は送信された合計バイト数を返します。これは len で示される数より小さい場合があります。 それ以外の場合は、SOCKET_ERRORの値が返され、 WSAGetLastError を呼び出すことによって特定のエラー コードを取得できます。

エラー コード 意味
WSANOTINITIALIZED
この関数を使用する前に、 WSAStartup 呼び出しが正常に行われる必要があります。
WSAENETDOWN
ネットワーク サブシステムが失敗しました。
WSAEACCES
要求されたアドレスはブロードキャスト アドレスですが、適切なフラグが設定されていません。 ブロードキャスト アドレスの使用を許可するには、SO_BROADCAST パラメーターを指定して setsockopt を呼び出します。
WSAEINVAL
不明なフラグが指定されたか、SO_OOBINLINEが有効になっているソケットに対してMSG_OOBが指定されました。
WSAEINTR
WSACancelBlockingCall を使用して、Windows ソケット 1.1 の呼び出しをブロックしているが取り消されました。
WSAEINPROGRESS
ブロックしている Windows Sockets 1.1 呼び出しが進行中であるか、サービス プロバイダーがコールバック関数を処理しています。
WSAEFAULT
buf パラメーターまたは to パラメーターがユーザー・アドレス・スペースの一部ではないか、tolen パラメーターが小さすぎます。
WSAENETRESET
操作の実行中にキープ アライブ動作によってエラーが検出されたため、接続が切断されました。
WSAENOBUFS
バッファーに空き領域がありません。
WSAENOTCONN
ソケットが接続されていません (接続指向のソケットのみ)。
WSAENOTSOCK
記述子はソケットではありません。
WSAEOPNOTSUPP
MSG_OOBが指定されましたが、ソケットが型SOCK_STREAM、OOB データがこのソケットに関連付けられている通信ドメインでサポートされていない、またはソケットが一方向であり、受信操作のみをサポートするなど、ストリーム スタイルではありません。
WSAESHUTDOWN
ソケットがシャットダウンされました。SD_SENDまたはSD_BOTHに設定された方法シャットダウンが呼び出された後にソケットに送信することはできません。
WSAEWOULDBLOCK
ソケットは非ブロッキングとしてマークされ、要求された操作はブロックされます。
WSAEMSGSIZE
ソケットはメッセージ指向であり、メッセージは基になるトランスポートでサポートされる最大値を超えています。
WSAEHOSTUNREACH
現時点では、このホストからリモート ホストにアクセスできません。
WSAECONNABORTED
仮想回線はタイムアウトまたはその他の障害のために切断されました。 ソケットが使用できないため、アプリケーションはソケットを閉じる必要があります。
WSAECONNRESET
強制終了または中止になる閉じる操作を実行するリモート側によって仮想回線がリセットされました。 UDP ソケットの場合、リモート ホストは以前に送信された UDP データグラムを配信できず、"ポートに到達できない" ICMP パケットで応答しました。 ソケットが使用できないため、アプリケーションはソケットを閉じる必要があります。
WSAEADDRNOTAVAIL
リモート アドレスが有効なアドレスではありません (たとえば、ADDR_ANY)。
WSAEAFNOSUPPORT
指定されたファミリーのアドレスをこのソケットと共に使用することはできません。
WSAEDESTADDRREQ
宛先アドレスが必要です。
WSAENETUNREACH
現在このホストからネットワークには到達できません。
WSAEHOSTUNREACH
到達できないホストに対してソケット操作を実行しようとしました。
WSAETIMEDOUT
ネットワーク障害のため、またはもう一方の側のシステムが予告なしにダウンしたため、接続が切断されました。

解説

sendto 関数は、ソケットに送信データを書き込むのに使用されます。 メッセージ指向ソケットの場合は、基になるサブネットの最大パケット サイズを超えないように注意する必要があります。これは、 getsockopt を 使用してソケット オプション SO_MAX_MSG_SIZEの値を取得することで取得できます。 データが長すぎて基になるプロトコルをアトミックに通過できない場合は、 エラー WSAEMSGSIZE が返され、データは送信されません。

to パラメーターには、ブロードキャストやマルチキャスト アドレスなど、ソケットのアドレス ファミリ内の任意の有効なアドレスを指定できます。 ブロードキャスト アドレスに送信するには、アプリケーションで setsockopt を使用し、SO_BROADCAST有効にする必要があります。 それ以外の場合、 sendto はエラー コード WSAEACCES で失敗します。 TCP/IP の場合、アプリケーションは任意のマルチキャスト アドレスに送信できます (グループ メンバーになることはありません)。

メモ ソケットが開かれた場合、 setsockopt 呼び出しが行われ、 sendto 呼び出しが行われると、Windows ソケットは暗黙的な バインド 関数呼び出しを実行します。
 
ソケットがバインドされていない場合は、システムによって一意の値がローカル関連付けに割り当てられ、ソケットはバインド済みとしてマークされます。 ソケットが接続されている場合は、 getsockname 関数を使用して、ソケットに関連付けられているローカル IP アドレスとポートを決定できます。

ソケットが接続されていない場合は、
getsockname 関数を使用してソケットに関連付けられているローカル ポート番号を確認できますが、返される IP アドレスは、指定されたプロトコルのワイルドカード アドレスに設定されます (たとえば、IPv4 の場合は INADDR_ANY または "0.0.0.0"、IPv6 の IN6ADDR_ANY_INIT場合は "::" です)。

sendto が正常に完了しても、データが正常に配信されたことを示すものではありません。

sendto 関数は、通常、コネクションレス ソケットで使用され、 to パラメーターによって識別される特定のピア ソケットにデータグラム送信します。 コネクションレス ソケットが以前に特定のアドレスに接続されていた場合でも、 to パラメーターは、その特定のデータグラムの宛先アドレスのみをオーバーライドします。 接続指向ソケットでは、to パラメーターと tolen パラメーターは無視され、sendto は send と同等になります。

メモsendto などのブロッキング Winsock 呼び出しを発行する場合、Winsock は、呼び出しを完了する前にネットワーク イベントを待機する必要がある場合があります。 Winsock は、この状況でアラート可能な待機を実行します。この待機は、同じスレッドでスケジュールされた非同期プロシージャ 呼び出し (APC) によって中断される可能性があります。 同じスレッドで進行中の Winsock 呼び出しを中断した APC 内で別のブロック Winsock 呼び出しを発行すると、未定義の動作が発生し、Winsock クライアントが試行してはなりません。
 

コード例

次の例では、 sendto 関数の使用方法を示します。
#ifndef UNICODE
#define UNICODE
#endif

#define WIN32_LEAN_AND_MEAN

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

// Link with ws2_32.lib
#pragma comment(lib, "Ws2_32.lib")

int main()
{

    int iResult;
    WSADATA wsaData;

    SOCKET SendSocket = INVALID_SOCKET;
    sockaddr_in RecvAddr;

    unsigned short Port = 27015;

    char SendBuf[1024];
    int BufLen = 1024;

    //----------------------
    // Initialize Winsock
    iResult = WSAStartup(MAKEWORD(2, 2), &wsaData);
    if (iResult != NO_ERROR) {
        wprintf(L"WSAStartup failed with error: %d\n", iResult);
        return 1;
    }

    //---------------------------------------------
    // Create a socket for sending data
    SendSocket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
    if (SendSocket == INVALID_SOCKET) {
        wprintf(L"socket failed with error: %ld\n", WSAGetLastError());
        WSACleanup();
        return 1;
    }
    //---------------------------------------------
    // Set up the RecvAddr structure with the IP address of
    // the receiver (in this example case "192.168.1.1")
    // and the specified port number.
    RecvAddr.sin_family = AF_INET;
    RecvAddr.sin_port = htons(Port);
    RecvAddr.sin_addr.s_addr = inet_addr("192.168.1.1");

    //---------------------------------------------
    // Send a datagram to the receiver
    wprintf(L"Sending a datagram to the receiver...\n");
    iResult = sendto(SendSocket,
                     SendBuf, BufLen, 0, (SOCKADDR *) & RecvAddr, sizeof (RecvAddr));
    if (iResult == SOCKET_ERROR) {
        wprintf(L"sendto failed with error: %d\n", WSAGetLastError());
        closesocket(SendSocket);
        WSACleanup();
        return 1;
    }
    //---------------------------------------------
    // When the application is finished sending, close the socket.
    wprintf(L"Finished sending. Closing socket.\n");
    iResult = closesocket(SendSocket);
    if (iResult == SOCKET_ERROR) {
        wprintf(L"closesocket failed with error: %d\n", WSAGetLastError());
        WSACleanup();
        return 1;
    }
    //---------------------------------------------
    // Clean up and quit.
    wprintf(L"Exiting.\n");
    WSACleanup();
    return 0;
}


IP を使用するソケットの場合 (バージョン 4)

ブロードキャストを送信するには (SOCK_DGRAMのみ)、to パラメーターによって指されるアドレス 構築して、特別な IPv4 アドレス INADDR_BROADCAST (Winsock2.h で定義) と、目的のポート番号を含めることができます。 to パラメーターが指すアドレス INADDR_BROADCASTアドレスと目的のポートが含まれている場合、ブロードキャストはそのポートにすべてのインターフェイスで送信されます。

ブロードキャストを特定のインターフェイスでのみ送信する必要がある場合は、 to パラメーターによって指されるアドレスに、インターフェイスと目的のポートのサブネット ブロードキャスト アドレスが含まれている必要があります。 たとえば、サブネット マスクが 255.255.255.0 である 192.168.1.0 の IPv4 ネットワーク アドレスでは、サブネット ブロードキャスト アドレス 192.168.1.255 が使用されます。

一般に、ブロードキャスト データグラムが断片化が発生する可能性があるサイズを超えることはできません。これは、データグラムのデータ部分 (ヘッダーを除く) が 512 バイトを超えないようにすることを意味します。

転送するデータを保持するためにトランスポート・システム内で使用可能なバッファー・スペースがない場合、ソケットが非ブロッキング・モードに入っていない限り、 sendto はブロックします。 非ブロッキング、ストリーム指向ソケットの場合、書き込まれるバイト数は、クライアントシステムとサーバーシステムの両方でのバッファーの可用性に応じて、1 から要求された長さの間にすることができます。 selectWSAAsyncSelect、または WSAEventSelect 関数を使用して、より多くのデータを送信できるタイミングを判断できます。

len が 0 の sendto を呼び出すことは許容され、有効な値として 0 を返します。 メッセージ指向ソケットの場合は、長さ 0 のトランスポート・データグラムが送信されます。

flags パラメーターを使用すると、関連するソケットに指定されたオプションを超えて関数呼び出しの動作に影響を与えることができます。 この関数のセマンティクスは、ソケット オプションと flags パラメーターによって決まります。 後者は、次のいずれかの値を持つビットごとの OR 演算子を使用して構築されます。

説明
MSG_DONTROUTE データをルーティングの対象にしないことを指定します。 Windows ソケット サービス プロバイダーは、このフラグを無視することを選択できます。
MSG_OOB OOB データを送信します (SOCK_STREAM などのストリーム スタイルのソケットのみ)。
 

Windows Phone 8: この関数は、Windows Phone 8 以降のWindows Phone ストア アプリでサポートされています。

Windows 8.1Windows Server 2012 R2: この関数は、Windows 8.1、Windows Server 2012 R2 以降の Windows ストア アプリでサポートされています。

要件

   
サポートされている最小のクライアント Windows 8.1、 Windows Vista [デスクトップ アプリ |UWP アプリ]
サポートされている最小のサーバー Windows Server 2003 [デスクトップ アプリのみ | UWP アプリ]
対象プラットフォーム Windows
ヘッダー winsock.h (Winsock2.h を含む)
Library Ws2_32.lib
[DLL] Ws2_32.dll

関連項目

WSAAsyncSelect

WSAEventSelect

Winsock 関数

Winsock リファレンス

Recv

recvfrom

select

送信

socket