Re: UDPデータ損失率
Posted: 2012年1月23日(月) 16:49
と言うことは史上最悪のデスペナさんの送信側プログラムに何らかの問題があると考えるのが妥当かと思います。
ところでWinscok2はws2_32.libを使われていますよね?
ところでWinscok2はws2_32.libを使われていますよね?
と書いてあったのでそれをリンクしてました。それ以降、他のサイトではその部分を流していたので・・・・・WinSockを使うにはちょっとクセがあって、[wsock32.lib]というライブラリーにリンクせねばなりません。
ごめんなさい、これのやり方がわかりません。教えてくださいsoftya(ソフト屋) さんが書きました:[追記]史上最悪のデスペナさんがリリースビルドしたプログラムを添付してもらって良いですか?
ソースレベルではなくexeレベルでチェックしたいです。
編集が遅かったのでお返事を既に頂いていたようですね。史上最悪のデスペナ さんが書きました:合ってるかはわかりませんが、DebugモードではなくReleaseモードでビルドしたときに以下のエラーが出ました
1>------ ビルド開始: プロジェクト: 01, 構成: Release Win32 ------
1>01.obj : error LNK2001: 外部シンボル "__imp__closesocket@4" は未解決です。
1>01.obj : error LNK2001: 外部シンボル "__imp__socket@12" は未解決です。
1>01.obj : error LNK2001: 外部シンボル "__imp__WSACleanup@0" は未解決です。
1>01.obj : error LNK2001: 外部シンボル "__imp__sendto@24" は未解決です。
1>01.obj : error LNK2001: 外部シンボル "__imp__htons@4" は未解決です。
1>01.obj : error LNK2001: 外部シンボル "__imp__inet_addr@4" は未解決です。
1>01.obj : error LNK2001: 外部シンボル "__imp__WSAStartup@8" は未解決です。
1>C:\Users\TO\Desktop\WinSock\05.UDP-1(単純) - コピー\Client\Release\01.exe : fatal error LNK1120: 外部参照 7 が未解決です。
========== ビルド: 0 正常終了、1 失敗、0 更新不要、0 スキップ ==========
まだ、これ出来てませんがファイアウォールやセキュリティソフトを切ったときの送信テストは以下のようになりましたsoftya(ソフト屋) さんが書きました:それと連続5回通信とかの機能を入れてみてください。送信文字列はHELLO0~HELLO4と変化するのが望ましいです。
これは、一回の送信毎に確率的に失敗するのか、何らかの初期化周りが成功すれば連続送信が成功するのか知りたいためです。
はい。そうですsoftya(ソフト屋) さんが書きました:デバッカを介さず直接exeを起動しても同じぐらいの確率ですか?
部分を
sendto( SendSock, "HELLO-0", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-1", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-2", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-3", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-4", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
printf("バージョン = %d.%d\n記述 = %s\n状態 = %s\n" ,
(BYTE)wsaData.wHighVersion , wsaData.wHighVersion >> 8 ,
wsaData.szDescription , wsaData.szSystemStatus
);
#include <stdio.h>
#include <winsock2.h>
int main()
{
WSAData wsaData;
SOCKET SendSock, RecvSock;
struct sockaddr_in ServerAddr;
int Flag;
WSAStartup(MAKEWORD(2,0), &wsaData);
Flag = WSAGetLastError();
printf("%d",Flag);
SendSock = socket(AF_INET, SOCK_DGRAM, 0);
printf("%d",Flag);
RecvSock = socket(AF_INET, SOCK_DGRAM, 0);
printf("%d",Flag);
ServerAddr.sin_family = AF_INET;
ServerAddr.sin_port = htons(4000);
ServerAddr.sin_addr.S_un.S_addr = inet_addr("127.0.0.1");
/* while(1)
{
SendFlag = sendto( SendSock, "HELLO", 5, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
if( SendFlag == 5 ) break;
}
*/
sendto( SendSock, "HELLO-0", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-1", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-2", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-3", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-4", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
printf("%d",Flag);
closesocket( SendSock );
closesocket( RecvSock );
printf("%d",Flag);
WSACleanup();
printf("%d",Flag);
return 0;
}
#include <stdio.h>
#include <winsock2.h>
int main()
{
WSAData wsaData;
SOCKET SendSock, RecvSock;
struct sockaddr_in ServerAddr;
int Flag;
WSAStartup(MAKEWORD(2,0), &wsaData);
Flag = WSAGetLastError();
printf("%d\n",Flag);
SendSock = socket(AF_INET, SOCK_DGRAM, 0);
Flag = WSAGetLastError();
printf("%d\n",Flag);
RecvSock = socket(AF_INET, SOCK_DGRAM, 0);
Flag = WSAGetLastError();
printf("%d\n",Flag);
ServerAddr.sin_family = AF_INET;
ServerAddr.sin_port = htons(4000);
ServerAddr.sin_addr.S_un.S_addr = inet_addr("127.0.0.1");
/* while(1)
{
SendFlag = sendto( SendSock, "HELLO", 5, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
if( SendFlag == 5 ) break;
}
*/
sendto( SendSock, "HELLO-0", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
Flag = WSAGetLastError();
printf("%d\n",Flag);
sendto( SendSock, "HELLO-1", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
Flag = WSAGetLastError();
printf("%d\n",Flag);
sendto( SendSock, "HELLO-2", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
Flag = WSAGetLastError();
printf("%d\n",Flag);
sendto( SendSock, "HELLO-3", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
Flag = WSAGetLastError();
printf("%d\n",Flag);
sendto( SendSock, "HELLO-4", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
Flag = WSAGetLastError();
printf("%d\n",Flag);
closesocket( SendSock );
closesocket( RecvSock );
Flag = WSAGetLastError();
printf("%d\n",Flag);
WSACleanup();
Flag = WSAGetLastError();
printf("%d\n",Flag);
return 0;
}
WSAGetLastError()を無くして戻り値だけのチェックsoftya(ソフト屋) さんが書きました:WSAGetLastError()だけでなく全部の戻り値をチェックして下さい。
#include <stdio.h>
#include <winsock2.h>
int main()
{
WSAData wsaData;
SOCKET SendSock, RecvSock;
struct sockaddr_in ServerAddr;
int InitFlag, BindFlag, SendFlag;
InitFlag = WSAStartup(MAKEWORD(2,0), &wsaData);
switch(InitFlag)
{
case WSASYSNOTREADY:
printf("ネットワークへの接続準備ができていない");
break;
case WSAVERNOTSUPPORTED:
printf("要求した WinSock のバージョンはこのシステムで提供されていない");
break;
case WSAEINPROGRESS:
printf("ブロッキング操作の実行中であるまたはサービスプロバイダがコールバック関数を処理している");
break;
case WSAEPROCLIM:
printf("WinSock が同時に処理できる最大プロセスに達成した");
break;
case WSAEFAULT:
printf("lpWSAData は有効なポインタではない");
break;
}
SendSock = socket(AF_INET, SOCK_DGRAM, 0);
if( SendSock == INVALID_SOCKET ) printf("送信ソケット作成エラー");
RecvSock = socket(AF_INET, SOCK_DGRAM, 0);
if( RecvSock == INVALID_SOCKET ) printf("受信ソケット作成エラー");
ServerAddr.sin_family = AF_INET;
ServerAddr.sin_port = htons(4000);
ServerAddr.sin_addr.S_un.S_addr = inet_addr("127.0.0.1");
int len = sendto( SendSock, "HELLO-0", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-1", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-2", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-3", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-4", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
if( len == SOCKET_ERROR ) printf("SOCKET_ERROR");
if( len < 7 ) printf("Short");
int Flag = closesocket( SendSock );
if( Flag == SOCKET_ERROR ) printf("SendSock_CLOSE_ERROR");
Flag = closesocket( RecvSock );
if( Flag == SOCKET_ERROR ) printf("RecvSock_CLOSE_ERROR");
WSACleanup();
return 0;
}
#include <stdio.h>
#include <winsock2.h>
int main()
{
WSAData wsaData;
SOCKET SendSock, RecvSock;
struct sockaddr_in ServerAddr;
int InitFlag, ErrorFlag;
InitFlag = WSAStartup(MAKEWORD(2,0), &wsaData);
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
switch(InitFlag)
{
case WSASYSNOTREADY:
printf("ネットワークへの接続準備ができていない");
break;
case WSAVERNOTSUPPORTED:
printf("要求した WinSock のバージョンはこのシステムで提供されていない");
break;
case WSAEINPROGRESS:
printf("ブロッキング操作の実行中であるまたはサービスプロバイダがコールバック関数を処理している");
break;
case WSAEPROCLIM:
printf("WinSock が同時に処理できる最大プロセスに達成した");
break;
case WSAEFAULT:
printf("lpWSAData は有効なポインタではない");
break;
}
SendSock = socket(AF_INET, SOCK_DGRAM, 0);
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
if( SendSock == INVALID_SOCKET ) printf("送信ソケット作成エラー");
RecvSock = socket(AF_INET, SOCK_DGRAM, 0);
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
if( RecvSock == INVALID_SOCKET ) printf("受信ソケット作成エラー");
ServerAddr.sin_family = AF_INET;
ServerAddr.sin_port = htons(4000);
ServerAddr.sin_addr.S_un.S_addr = inet_addr("127.0.0.1");
/* while(1)
{
SendFlag = sendto( SendSock, "HELLO", 5, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
if( SendFlag == 5 ) break;
}
*/
int len = sendto( SendSock, "HELLO-0", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-1", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-2", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-3", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
sendto( SendSock, "HELLO-4", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
if( len == SOCKET_ERROR ) printf("SOCKET_ERROR");
if( len < 7 ) printf("Short");
int Flag = closesocket( SendSock );
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
if( Flag == SOCKET_ERROR ) printf("SendSock_CLOSE_ERROR");
Flag = closesocket( RecvSock );
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
if( Flag == SOCKET_ERROR ) printf("RecvSock_CLOSE_ERROR");
WSACleanup();
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
return 0;
}
前略
int len = sendto( SendSock, "HELLO-0", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
if( len == SOCKET_ERROR ) printf("SOCKET_ERROR");
if( len < 7 ) printf("Short");
len = sendto( SendSock, "HELLO-1", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
if( len == SOCKET_ERROR ) printf("SOCKET_ERROR");
if( len < 7 ) printf("Short");
len = sendto( SendSock, "HELLO-2", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
if( len == SOCKET_ERROR ) printf("SOCKET_ERROR");
if( len < 7 ) printf("Short");
len = sendto( SendSock, "HELLO-3", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
if( len == SOCKET_ERROR ) printf("SOCKET_ERROR");
if( len < 7 ) printf("Short");
len = sendto( SendSock, "HELLO-4", 7, 0, (struct sockaddr *)&ServerAddr, sizeof(ServerAddr) );
ErrorFlag = WSAGetLastError();
printf("%d\n",ErrorFlag);
if( len == SOCKET_ERROR ) printf("SOCKET_ERROR");
if( len < 7 ) printf("Short");
後略
これはどこに入れたらいいんでしょう?softya(ソフト屋) さんが書きました:あとServerAddrの内容をクリアしたらどうなります?
memset(&ServerAddr, 0x00, siezof(ServerAddr));
これも実験しました。softya(ソフト屋) さんが書きました:この事実から、私が予想するのはsendto()からclosesocket()の間にSleepが必要なのではないか?って事なのですが実験してもらえますか?ほかはSleepを外して下さい。
と同じ結果になりました。史上最悪のデスペナ さんが書きました:エラーチェック、戻りチェック一切なし&memset無し&一部のsendto後のみSleep(100)
→その後にSleepしなかったsendtoは送信されないことあり。
追記:Hello0に限ってはそれのみ送信されることもある
とNo.39softya(ソフト屋) さんが書きました: 「UDP/IPテストツールの詳細情報 : Vector ソフトを探す!」
http://www.vector.co.jp/soft/winnt/net/se478370.html
を組み合わせて,01.exe -> UDP/IPテストツールのテストを試みました.史上最悪のデスペナ さんが書きました: よろしくお願いします
01.zip
だそうです。513 回目までは正しく送信できているのですが、 514~1623 まではデータがサーバに届いていません。 その後も、89449~97804、97871~98469、98536~100000 は紛失し、結局届いたのは 100,000 分の 3,618。 到達率 3.6%、つまり
データ損失率 96.4%
というものすごいことになっています。
そのUDPはLinuxっぽいですね。史上最悪のデスペナ さんが書きました: そういえばこんなサイト見つけました
513 回目までは正しく送信できているのですが、 514~1623 まではデータがサーバに届いていません。 その後も、89449~97804、97871~98469、98536~100000 は紛失し、結局届いたのは 100,000 分の 3,618。 到達率 3.6%、つまり
データ損失率 96.4%
というものすごいことになっています。
softya(ソフト屋) さんが書きました:受信バッファのあふれではないか?って事みたいです。
送信側の問題かと思ったら確かに受信側の方もありえますね。史上最悪のデスペナ さんが書きました:結論:sendtoの後ある程度の時間を置かないとバッファ(?)が上書きされるなどの状況が発生し、送信が行われなくなることがある。
このPCはリカバリディスク(OS)の付属して無いタイプ(その分安価)なのでインストールは無理ですね・・・・・softya(ソフト屋) さんが書きました:OSを新規インストールするとか同じPCに別OSをインストールして試してみるとか根幹周りの動作確認が不可欠です。
12時間も出来るような時が無いのですが12時間じゃなくてもいいのでしょうか?softya(ソフト屋) さんが書きました:「CPUに意図的に負荷を掛けて不具合が無いかチェックするフリーソフト「Prime95」 | aquapple (archives)」
そういえば、一時期ネットに繋ぐと数時間おきにブルースクリーン&強制再起動になったことがあるのですが・・・・・(スタンドアロンでは起こらず)softya(ソフト屋) さんが書きました:ただ、他にも問題が出そうなものですが
リカバリディスク(OS)が付属していなくてもリカバリ方法は提供されているはずです。史上最悪のデスペナ さんが書きました:このPCはリカバリディスク(OS)の付属して無いタイプ(その分安価)なのでインストールは無理ですね・・・・・
手順を印刷しないといけませんが明日にならないと印刷できる環境にならないので明日やる予定ですsoftya(ソフト屋) さんが書きました:「パソコン故障を無料ツール「 Ultimate Boot CD 」で検査する」
確かに!梨樹 さんが書きました:あんまり関係ないかもしれませんけど、バージョンが2.2なのにWSAStartupに2.0を要求して大丈夫なんでしょうか。
WSAStartup(MAKEWORD(2,2), &wsaData);
としてみてらどうでしょう。
何かの見間違いでしたらすみません。
50枚組980円で買ったのがリカバリできません、と言われて残り49枚が使われぬままもうすぐ2年が経ちますね~softya(ソフト屋) さんが書きました:50枚のスピンドルで買っても1200~1300円ぐらい10枚なら割高ですが500円ぐらいで買えます。
国産メーカーじゃない香りがする値段ですね。まぁ、国産でもたまに失敗しますけど。太陽誘電よりもTDK国産の方が失敗する確率が低い気がしますのでメーカー製を買われたほうが良いと思います。史上最悪のデスペナ さんが書きました:50枚組980円で買ったのがリカバリできません、と言われて残り49枚が使われぬままもうすぐ2年が経ちますね~
DVD-Rだから使い捨てみたいなものだし・・・・・・長期保存するようなの無いですし・・・・・
それは失敗する利用になりません。史上最悪のデスペナ さんが書きました:そうだ、基本事項が抜けてました。このPCはノートです
ディスクを買う方が、突然OSが起動しなくってOSを買うだけのために2万円を出すよりよっぽど良いと思うんですが。史上最悪のデスペナ さんが書きました:近くに電気店が無いので、売ってるとこに行こうとするとまとまった時間がなかなか取れないんですよね^^;
USB一個じゃ足りないので、安売りしてると欲しいと思うのですが結局行けずに諦めたり・・・・・・
出来るだけ早く対処しなければならないのは分かってるんですが・・・・・・
何故かCDに焼けなかったです・・・・・・softya(ソフト屋) さんが書きました:「パソコン故障を無料ツール「 Ultimate Boot CD 」で検査する」