UDPソケットを使用してCで簡単なカウントダウンアプリケーションを実装しようとしています。 アプリケーションのサーバー部分に非常に奇妙な問題があります。クライアントから番号を受け取り、カウントダウンに異なる番号を送信する必要があります。たとえば、ユーザーがクライアントに5を入力すると、サーバーは5を受信し、クライアントに4,3,2,1、0を送信する必要があります。単純なクライアント/サーバーカウントダウンCアプリケーションでの異常な動作
#define BUFFERSIZE 512
#define PORT 55123
void ClearWinSock()
{
#if defined WIN32
WSACleanup();
#endif
}
int main()
{
#if defined WIN32
WSADATA wsaData;
WORD wVersionRequested;
wVersionRequested = MAKEWORD(2, 2);
if(WSAStartup(wVersionRequested, &wsaData) != 0)
{
printf("Error: unable to initialize the socket!\n");
return -1;
}
#endif
int mainSocket = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP);
if(mainSocket < 0)
{
printf("Error: unable to create the socket!\n");
ClearWinSock();
return -1;
}
struct sockaddr_in serverSockAddrIn;
memset(&serverSockAddrIn, 0, sizeof(serverSockAddrIn));
serverSockAddrIn.sin_family = AF_INET;
serverSockAddrIn.sin_port = htons(PORT);
serverSockAddrIn.sin_addr.s_addr = inet_addr("127.0.0.1");
if(bind(mainSocket, (struct sockaddr*) &serverSockAddrIn, sizeof(serverSockAddrIn)) < 0)
{
fprintf(stderr, "Error: unable to bind the socket!\n");
ClearWinSock();
return -1;
}
char buffer[BUFFERSIZE];
struct sockaddr_in clientAddress;
unsigned int clientAddressLength;
int recvMessageSize;
while(1)
{
clientAddressLength = sizeof(clientAddress);
recvMessageSize = recvfrom(mainSocket, buffer, BUFFERSIZE, 0, (struct sockaddr*) &clientAddress, &clientAddressLength);
int countdownValue;
sscanf(buffer, "%d", &countdownValue);
printf("\nNumber received: %d\n", countdownValue);
int index;
for(index = countdownValue - 1; index >= 0; --index)
{
itoa(index, buffer, 10);
int outputStringLength = strlen(buffer);
if(sendto(mainSocket, buffer, outputStringLength, 0, (struct sockaddr*) &clientAddress, sizeof(clientAddress)) != outputStringLength)
{
printf("Error: unable to send the message!");
}
}
}
ClearWinSock();
return 0;
}
今の問題は、私は、例えば、クライアントからの5番を送信する場合、時々、サーバーが正常に動作することで、時にはそれが「番号が受信:5」を言う:、送信されません。ここに私のコードですそれからそれは "Number received:0"と5回言います。
私はソケットを使って何か間違っていると思います。それとも、バッファーのクリーニングが必要なのでしょうか?私はエラーを再現することはできません。なぜなら、同じ入力では時にはそれはある意味で、時には他のもので動作するからです。
何か:
また、あなたは常にバインド()を呼び出す前に次のコードを実行することによって、同じポートを共有するために、クライアントとサーバーの両方を指示することができますか?私はrecvfromの前にバッファをきれいにしようとしましたが、変更されません。 – JohnQ
これでエラーを再現する方法を知っています。サーバーの前でクライアントを起動するとアプリケーションが動作しません。私がサーバを起動してからクライアントを起動すると、すべてOKです。たぶんソケット初期化の何かですか? – JohnQ