• 締切済み

UDP通信について

前回のことでかなり言われたので改変版を見てもらいたいと思います。 TCPと伝えていましたが今回、UDPに変えました。 ヘッダーはこのようになっております。 ==wsock.h== #include <Windows.h> #include <stdio.h> #pragma comment(lib,"WSock32.lib") #define PORT_NO 8000 ポート番号 #define SERVER_NAME "" enum MINE{ NONE, SERVER, CLIENT }; ソケット通信 class WSOCK{ private: WSADATA wsaData; SOCKET s; SOCKADDR_IN saddr; int rtn; int state; MINE mineFlg; char szStr[256]; エラーメッセージ用 u_short port; 変換後のポート番号 int fromlen; 受信したサイズ HOSTENT *lpHost; ホスト情報 ファイルディスクプリタをまとめた構造体 //→ソケット判別する為の管理情報 fd_set fds,readfds; public: char szRcvBuf[1024]; 受信バッファ char szSndBuf[1024]; 送信バッファ SOCKADDR_IN from; ソケットアドレス構造体 WSOCK(); ~WSOCK(); bool ServerRcv(); 受信 bool ServerSnd();送信 bool CliantRcv();受信 bool CliantSnd();送信 void SarverSet(); void ClientSet(); bool EnumMyIPAddress(); }; ==wsock.cpp== #include "wsock.h" コンストラクタ WSOCK::WSOCK(){ //WinSock初期化 rtn = WSAStartup(MAKEWORD(2,2),&wsaData); if(rtn != 0){ MessageBox(NULL,"WSAStartup失敗", "ERROR",MB_OK); state = -1; } ソケットを開く s = socket(AF_INET,SOCK_DGRAM,0); if(s<0){ MessageBox(NULL,"ソケットをオープンできません", "eRROR",MB_OK); WSACleanup(); state = 2; } 0で初期化 memset(&saddr,0,sizeof(SOCKADDR_IN)); saddr.sin_family = AF_INET;//アドレスファミリー saddr.sin_port = htons(PORT_NO);//ポート mineFlg = SERVER; サーバ側設定 if(mineFlg == SERVER) { SarverSet(); } if(mineFlg == CLIENT) {クライアント ClientSet(); } } WSOCK::~WSOCK(){ closesocket(s); ソケットのリソース解放 rtn = WSACleanup(); if(rtn == SOCKET_ERROR){ MessageBox(NULL,"WSACleanup失敗","ERrOR",MB_OK); state = -2; } } //受信 bool WSOCK::ServerRcv(){ 読み込み用fd_setの初期化 selectが毎回内容を上書きしてしまうので毎回初期化 memcpy(&fds,&readfds,sizeof(fd_set)); struct timeval timeout = {0,0};   //{1秒以上の部分()s、1秒以下の部分(ms)} fdsに設定されたソケットが読み込み可能になるまで待つ select(0,&fds,NULL,NULL,&timeout); ソケット読み込み可能データがある場合 if(FD_ISSET(s,&fds)){ fromlen = (int)sizeof(from); //nullで初期化 memset(szRcvBuf,'\0',sizeof(szRcvBuf)); //受信処理 rtn = recvfrom(s,szRcvBuf,(int)sizeof(szRcvBuf)-1,0, (SOCKADDR*)&from,&fromlen); if(rtn == SOCKET_ERROR){ MessageBox(NULL,"recvfromエラー","ERRoR",MB_OK); return false; } } szRcvBuf[rtn] | '\0';//NULLコード if(strcmp(szRcvBuf,"c_end") == 0){ MessageBox(NULL,"クライアントが接続を切りました","ERROr",MB_OK); return false; } return true; } 送信 bool WSOCK::ServerSnd(){ char buf[1024]; memset(buf,0,sizeof(buf)); //_snprintf:書式指定文字付きデータ書き込み _snprintf(buf,sizeof(buf),"data to port 8000"); //送信処理 rtn = sendto(s,szSndBuf,(int)strlen(szSndBuf)+1, 0,(LPSOCKADDR)&from, 送り先サーバ/クライアント sizeof(from)); サイズ if(rtn != (int)strlen(szSndBuf)+1){ MessageBox(NULL,"sendtoエラー","サーバーエラ",MB_OK); closesocket(s); WSACleanup(); return false; } return true; } 受信 bool WSOCK::CliantRcv(){ fromlen = (int)sizeof(from); //nullで初期化 memset(szRcvBuf,'\0',sizeof(szRcvBuf)); //受信処理 rtn = recvfrom(s,szRcvBuf,(int)sizeof(szRcvBuf)-1,0, (SOCKADDR*)&from,&fromlen); if(rtn == SOCKET_ERROR){ MessageBox(NULL,"recvfromエラー","ERRoR",MB_OK); return false; } szRcvBuf[rtn] | '\0'; //NULLコード if(strcmp(szRcvBuf,"s_end") == 0){ MessageBox(NULL,"接続を切りました","ERROr",MB_OK); return false; } return true; } 送信 bool WSOCK::CliantSnd(){ 送信処理 rtn = sendto(s,szSndBuf,(int)strlen(szSndBuf)+1, 0,(LPSOCKADDR)&saddr, 送り先サーバ/クライアント sizeof(saddr)); サイズ if(rtn != (int)strlen(szSndBuf)+1){ MessageBox(NULL,"sendtoエラー","erROR",MB_OK); closesocket(s); WSACleanup(); return false; } return true; } void WSOCK::SarverSet(){ saddr.sin_addr.s_addr = htonl(INADDR_ANY); ソケットにローカルアドレスを関連付ける if(bind(s,(LPSOCKADDR)&saddr, (int)sizeof(saddr)) == SOCKET_ERROR){ MessageBox(NULL,"bindエラー","er",MB_OK); closesocket(s); WSACleanup(); state = -3; } FD_ZERO(&readfds); FD_SET(s,&readfds); } void WSOCK::ClientSet(){    クライアント側設定    ホスト名からホスト情報を取得 lpHost = gethostbyname(SERVER_NAME); サーバのアドレスをセット memcpy(&(saddr.sin_addr), lpHost->h_addr_list[0], //サーバのアドレス lpHost->h_length); } となっております。

みんなの回答

  • zwi
  • ベストアンサー率56% (730/1282)
回答No.3

UDPの場合はルータ越えの問題もあるからブロードバンド・ルータを間に挟むならポート開放が必須です。このポート開放がクライアント側にも発生するという非常に初心者向きじゃないので避けたほうが良いと思います。

回答No.2

なぜTCPではなくUDPを選択したのでしょう? 単にTCPを使ってみたけどうまく通信できなかったから、とか、TCPではデータが意図せず分割されたり統合されたりして受信側の処理が面倒になるから、などという理由でTCPを使わずUDPを選んだのだとしたら絶対にやめておくべきです。 UDPは信頼性の低いプロトコルと言われるだけあって、 ・パケットの順序が保証されない。送信側で「AAA」「BBB」「CCC」の順に送信したのに、受信側には「CCC」「AAA」「BBB」の順に届くかもしれない。 ・パケットが破棄されるかもしれない。送信側で「AAA」「BBB」「CCC」と送信したのに、受信側には「AAA」「CCC」だけ届くかもしれない。 ・1つのパケット送信に対して1回だけ受信するとは限らない。送信側で「AAA」「BBB」と送信したら、受信側では「AAA」「AAA」「BBB」と届くかもしれない。 などなどの様々な問題をクリアしていかなければいけないのですが。 もし、あなたがこれらの課題を自分のプログラムの中で解決できるか、作ろうとしているプログラムでは通信でこれらの現象が発生しても問題ないというのであれば、UDPを使い続けても問題ないでしょう。もしそうでなければ、TCPに戻すべきだと思います。 UDPを使うのは以下のような場合でしょうか…。 ・TCPじゃ間に合わないくらいのリアルタイム性が要求される場合 ・データがある程度失われてもどうにかなる場合 ・通信データ量が小さく、上記問題も簡単に解決できるか、そもそも考慮する必要がない場合

回答No.1

別アカウントですが同じ質問者です。 通信している場所はこちらになります。 やりたいことはボードゲームの通信です。 ずっと通信をしてなにかアクションがあればアクションがあったchar型をもたせて受信側に送り、ターンチェンジする方法を行いたいと思っております。 その方法がわかりません。 すみませんがアドバイスよろしくお願いします(>人<;) //受信 switch(mineFlg) { case NONE: break; case SERVER: //受信 ServerRcv(); if(lstrlen(szRcvBuf) > 0) { if(strncmp(szRcvBuf,"NULL",3) == 0) { char strEx[4]; memset(strEx,'\0',sizeof(strEx)); flg = true; } } if(flg){ //送信情報の作成 memset(szSndBuf,'\0',sizeof(szSndBuf)); wsprintf(szSndBuf,"NULL"); //送信処理 ServerSnd(); } break; case CLIENT: //送信情報の作成 memset(szSndBuf,'\0',sizeof(szSndBuf)); wsprintf(szSndBuf,"NULL"); //送信処理 CliantSnd(); //受信 CliantRcv(); if(lstrlen(szRcvBuf) > 0){ if(strncmp(szRcvBuf,"NULL",3) == 0){ char strEx[4]; memset(strEx,'\0',sizeof(strEx)); } if(strncmp(szRcvBuf,"clear",3) == 0){ char strEx[4]; memset(strEx,'\0',sizeof(strEx)); for(int i=0;i<PIECE_RANGE;i++){ memcpy(strEx,&szRcvBuf[3],3); Piece_Black[i].vecPos.x = atoi(strEx); memcpy(strEx,&szRcvBuf[6],3); Piece_Black[i].vecPos.z = atoi(strEx); } } } break; }

関連するQ&A

  • ゲームの通信プログラムについてなんですが

    ボードゲームで対戦用にとTCP通信プログラムを導入したいのですがどうにもうまくいきません。 ゲームのところでつながっているにはつながっているんですが無限ループのように通信しているようなんです。 VisualStudio2010とwinsocketを使っております。 サーバーのプログラムはこうです。 void COMMU::SERWSA() { port = 6543; //WinSock初期化 rtn = WSAStartup( MAKEWORD(2,2), &wsaData); } void COMMU::SERSOCK() { listen_s = socket( AF_INET, SOCK_STREAM, 0); if(listen_s < 0)     { WSACleanup(); return; } //0で初期化 memset(&saddr, 0, sizeof(SOCKADDR_IN)); saddr.sin_family = AF_INET; saddr.sin_port = htons(port); saddr.sin_addr.s_addr = INADDR_ANY; if(bind(listen_s, (struct sockaddr *)&saddr, sizeof(saddr)) == SOCKET_ERROR)     { closesocket(listen_s); WSACleanup(); return; } } void COMMU::SERLIS() { //クライアントからの接続待ち状態にする if(listen(listen_s, 0) == SOCKET_ERROR) { closesocket(listen_s); WSACleanup(); return; } fromlen = (int)sizeof(from); s = accept(listen_s, (SOCKADDR *)&from, &fromlen); if(s == INVALID_SOCKET)     { closesocket(listen_s); WSACleanup(); return; }else{ inet_ntoa(from.sin_addr); } //リスンソケットはもう不要 closesocket(listen_s); MessageBox(NULL,"繋がった","読み込みエラー", MB_OK |MB_ICONERROR); } COMMU::~COMMU() { if(shutdown(s, SD_BOTH) != 0){ perror("シャットダウンに失敗しました\n"); } //ソケットのクローズ closesocket(s); //ソケットのリソース解放 rtn = WSACleanup(); if(rtn == SOCKET_ERROR){ fprintf(stderr, "WSACleanup失敗\n"); return; } printf("WSACleanup成功\n"); printf("サーバ終了\n"); } 続いてクライアントです。 void Client::CLWSA() { //ポート番号の入力 port = 6543; //数値に変換 //WinSock初期化 rtn = WSAStartup( MAKEWORD(2,2),//上位と下位を指定してWORDデータを返すマクロ &wsaData); } void Client::CLSOCK() { //ソケットを開く s = socket( AF_INET, //アドレスファミリ SOCK_STREAM, //TCP(接続型通信)で通信 0); //プロトコル(0:WinSockが自動的に判断) if(s < 0){ //perror("ソケットをオープンできません\n"); WSACleanup(); return; } //ホスト名からホスト情報を取得 lpHost = gethostbyname("PC○○"); if(lpHost == NULL)     { addr = inet_addr(szServer); //ネットワークアドレスからホスト情報を取得 lpHost = gethostbyaddr((char*)&addr,4,AF_INET); } if(lpHost == NULL)    { printf("ホスト情報取得エラー\n"); closesocket(s); WSACleanup(); getchar(); return; } } void Client::CLCONNE() { //0で初期化 memset(&saddr, 0, sizeof(SOCKADDR_IN)); saddr.sin_family = lpHost->h_addrtype; //ホストのアドレスファミリ saddr.sin_port = htons(port); saddr.sin_addr.s_addr = *((u_long *)lpHost->h_addr); //接続要求する if(connect(s, (SOCKADDR *)&saddr, sizeof(saddr)) == SOCKET_ERROR){ printf("connectエラー\n"); closesocket(s); WSACleanup(); getchar(); return; }else{ MessageBox(NULL,"つながりました","読み込みエラー", MB_OK |MB_ICONERROR); } } Client::~Client() { if(shutdown(s, SD_BOTH) != 0){ perror("シャットダウンに失敗しました\n"); } //ソケットのクローズ closesocket(s); //ソケットのリソース解放 rtn = WSACleanup(); if(rtn == SOCKET_ERROR){ fprintf(stderr, "WSACleanup失敗\n"); return; } printf("WSACleanup成功\n"); printf("クライアント終了\n"); } です。 わかりにくいかと思いますがかなり困ってます・・・ 回答よろしくお願いします。

  • ソケット通信時のWSACleanup処理のエラーについて

    はじめまして。 現在、C++ Builder ver6.0 にて、ソケット通信のプログラムを作成しているのですが、受信処理を一定回数行うとwinsockのリソースを解放するWSACleanupが失敗してしまいます。1ファイル受信するごとに下記のソケットの初期化処理を入れています。 bool __fastcall CUdpSock::Init(void) {   WORD wVersionRequested; // socket version   int errorStatus;   WSADATA wsaData;   /* WinSockの初期化を行う */   wVersionRequested = MAKEWORD(1, 1); // バージョン 1.1 を要求する   nErrorStatus = WSAStartup(wVersionRequested, &wsaData);   if ( nErrorStatus != 0 )   {     m_msg.printf("WinSockの初期化失敗\n");     Application->MessageBox(m_msg.c_str(), "ソケットの初期化", MB_ICONINFORMATION | MB_OK);     return false;   }   if (atexit((void (*)(void))(WSACleanup))) // 終了時にWinSockのリソースを解放するようにしておく   {     m_msg.printf("atexit(WSACleanup)失敗\n");     Application->MessageBox(m_msg.c_str(), "ソケットの初期化", MB_ICONINFORMATION | MB_OK);     return false;   }   return true; } 現状、32回連続で受信した後、上記のWSACleanupで失敗になっています。 このような現象の場合、まずどのあたりを疑うべきでしょうか? 曖昧ですがご教授よろしくお願いします。

  • winsockと、gmail。

    現在、 http://kumei.ne.jp/c_lang/sdk3/sdk_229.htm を参考にして、gmailに向けてメールを送信する プログラムを書いております。 が、メールを送信する前のconnectの部分で失敗してしまいます。 ソースは以下の通りです。 void main() { WSADATA wsaData; LPHOSTENT lpHost; LPSERVENT lpServ; SOCKET s; int iProtocolPort, iRtn; SOCKADDR_IN sockadd; const char*szServerName = "smtp.gmail.com"; if (WSAStartup(MAKEWORD(1, 1), &wsaData) != 0) { MessageBox(NULL, "エラーです", "Error", MB_OK); return; } lpHost = gethostbyname(szServerName); if (lpHost == NULL) { MessageBox(NULL, "サーバが見つかりません", "Error", MB_OK); return; } s = socket(PF_INET, SOCK_STREAM, 0); if (s == INVALID_SOCKET) { MessageBox(NULL, "ソケットをオープンできません", "Error", MB_OK); return; } lpServ = getservbyname("mail", NULL); if (lpServ == NULL) { MessageBox(NULL, "ポート指定がされていないので、デフォルトを使います", "OK", MB_OK); iProtocolPort = htons(IPPORT_SMTP); } else { iProtocolPort = lpServ->s_port; } sockadd.sin_family = AF_INET; sockadd.sin_port = iProtocolPort; sockadd.sin_addr = *((LPIN_ADDR)*lpHost->h_addr_list); if (connect(s, (PSOCKADDR)&sockadd, sizeof(sockadd))) { /*ここでWSAGetLastError()をすると、WSAETIMEDOUTが返ってきます。*/ MessageBox(NULL, "サーバーソケットに接続失敗", "Error", MB_OK); return; } /*以下続く*/ } 上にあるように、connectの部分でタイムアウトになるようです。 当方、これらに関する周辺知識が足りておらず、 一体どこが間違えているのかすらわかりません。 どなたかこれが上手くいかない原因がわかる方、 是非、ご教授お願いします。

  • VC++のHTTP通信

    VC++2010でHTTP通信のサンプルプログラムを走らせてみたのですが、どうも上手く行きません。 ソースは以下の通りです。 #include <stdio.h> #include <winsock2.h> int main() { WSADATA wsaData; LPHOSTENT lpHost; SOCKET s; int nRtn; SOCKADDR_IN sockadd; char szServer[256], szURL[256], szStrRcv[1024], szPort[8]; char szStr[256], szYN[4]; u_short port; unsigned int addr; while (1) { // WinSockを初期化 if (WSAStartup(MAKEWORD(1, 1), &wsaData) != 0) { perror("WSAStartupエラーです\n"); return -1; } // サーバ名、ポート番号、ファイル名を取得 printf("Webサーバ名----"); gets_s(szServer); printf("ポート番号----"); gets_s(szPort); if (strcmp(szPort, "") == 0) strcpy_s(szPort, "80"); port = (u_short)atoi(szPort); printf("ファイル名----"); gets_s(szURL); if (strcmp(szURL, "") == 0) strcpy_s(szURL, "/"); // ソケットをオープン s = socket(PF_INET, SOCK_STREAM, 0); if (s == INVALID_SOCKET) { perror("ソケットをオープンできません\n"); WSACleanup(); return -2; } // ホスト名からホスト情報を取得 lpHost = gethostbyname(szServer); if (lpHost == NULL) { // アドレスを表す文字列を数値表現に変換 addr = inet_addr(szServer); // ネットワークアドレスからホスト情報を取得 lpHost = gethostbyaddr((char *)&addr, 4, AF_INET); if (lpHost == NULL) { wsprintf(szStr, "%sが見つかりません\n", szServer); perror(szStr); WSACleanup(); return -3; } } // SOCKADDR_IN構造体に必要事項をセット memset(&sockadd, 0, sizeof(sockadd)); sockadd.sin_family = AF_INET; sockadd.sin_port = htons(port); sockadd.sin_addr = *((LPIN_ADDR)*lpHost->h_addr_list); // ソケットに接続 if (connect(s, (PSOCKADDR)&sockadd, sizeof(sockadd)) != 0) { perror("サーバソケットに接続失敗\n"); closesocket(s); WSACleanup(); return -4; } // GETリクエストを送信 wsprintf(szStr, "GET %s HTTP/1.0\r\n\r\n", szURL); nRtn = send(s, szStr, (int)strlen(szStr), 0); while(1) { // 受信用バッファ(szStrRcv)をゼロクリア memset(szStrRcv, '\0', sizeof(szStrRcv)); // データを受信 nRtn = recv(s, szStrRcv, (int)sizeof(szStrRcv) - 1, 0); // 受信したデータを標準出力に書き出す printf("%s", szStrRcv); if (nRtn == 0) break; if (nRtn == SOCKET_ERROR) { perror("recvエラーです\n"); break; } } if (shutdown(s, SD_BOTH) != 0) { // シャットダウン perror("シャットダウンに失敗しました\n"); } closesocket(s); // ソケットをクローズ WSACleanup(); // WinSockのリソースを解放 printf("\nもう一度実行しますか(Y/N)----"); gets_s(szYN); if (strcmp(szYN, "n") == 0 || strcmp(szYN, "N") == 0) break; } return 0; } 例えば、ttp://kumei.jp/c_lang/を開こうしとて、 kumei.jp 80 /c_lang/index.html と入力した場合は上手くレスポンスが帰ってきますが、 googleに接続しようと思い、 www.google.co.jp 80 / と入力すると 302 Moved と帰ってきます。 しかし www.google.co.jp 80 www.google.co.jp と入力した場合は問題なくgoogleのトップページが帰ってきます。 また、ttp://hako.gob.jp/にアクセスしようとして、 hako.gob.jp 80 /index.html と入力した場合 DOMAIN ERROR が帰ってきます。 さらに、 hako.gob.jp 80 hako.gob.jp と入力すると 400 エラーが帰って来ました。 私はwindowsプログラムに関しては全くの素人で分からない事だらけの状態です。できるだけ分り易く書いて頂けると嬉しいです。私が教えて頂きたいことは以下のことです。 ・サイト(通信相手?)による違いはどこで生まれるのでしょうか? ・また、正しくはどのように入力すれば良いのでしょうか?それはどうすれば分かるのでしょうか? ・アドレスを指定しただけであとはプログラムに自動で判断してもらうにはどうすれば良いでしょうか? ・そもそも、このプログラムでは根本的に不可能な事をやろうとしているのでしょうか?もしそうであった場合どうすれば良いでしょうか? 質問だらけで申し訳ありません。誰か分かる方がいらっしゃれば教えて下さい。

  • UDP通信について

    UDP通信で困っています。 TCP/IP通信はすぐにうまくいったのですが、 UDPの簡単なサンプルがちゃんと動きません。 間違いがあればご指摘ください。 よろしくお願いします。 (クライアント側ソース int sock; struct sockaddr_in din; memset(&din, 0, sizeof(din)); din.sin_port = htons(50050); din.sin_family = AF_INET; din.sin_addr.s_addr = inet_addr("サーバーIP"); sock = socket(AF_INET, SOCK_DGRAM, 0); int buf = 12345; sendto(sock,(char*)&buf,sizeof(int),0,(struct sockaddr*)&din,sizeof(struct sockaddr_in)); (サーバー側ソース int sock; struct sockaddr_in sin; sock = socket(AF_INET, SOCK_DGRAM, 0); memset(&sin, 0, sizeof(sin)); sin.sin_family = AF_INET; sin.sin_port = htons(50050); sin.sin_addr.s_addr = htonl(INADDR_ANY); if(bind(sock, (struct sockaddr *) &sin, sizeof(sin)) < 0) { return(1); } struct sockaddr_in fromaddr; socklen_t len = sizeof(struct sockaddr_in); int buf; recvfrom(sock,(char*)&buf,sizeof(int),0,(struct sockaddr*)&fromaddr,&len); printf("recv:%d\n",buf);

  • TCP/IP通信型大文字・小文字変換プログラム

    TCP/IP通信型大文字・小文字変換プログラムを作りたいです。 しかし、うまく2つのプログラムが接続されません。 恐らく、IPアドレスやホスト名の問題だと思います。 超初心者でそこのところをあまり理解していません。 どなたかプログラムの補足をお願いします。 概要は ・クライアント キーボードから文字列を入力し、サーバーに送信。 サーバーから送信された文字列を画面に出力。 ・サーバー クライアントから送信された文字列に対し、 大文字は小文字に、小文字は大文字に変換して返す。 クライアント側プログラム #include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <sys/socket.h> #include <arpa/inet.h> #include <netinet/in.h> #define SOCK_NAME "./socket" int main() { struct sockaddr_in saddr; int soc; char buf[1024]; if ( (soc =socket(AF_INET, SOCK_STREAM, 0 ) ) < 0 ) { perror("socket"); exit(1); } memset((char *)&saddr, 0, sizeof(saddr)); saddr.sin_family = AF_INET; saddr.sin_addr.s_addr=inet_addr("192.168.1.1"); saddr.sin_port=htons(1357); if(connect(soc, (struct sockaddr *)&saddr, sizeof(saddr)) < 0) { perror("connect"); exit(1); } fprintf(stderr, "Connection established: socket %d used.\n", soc); while(fgets(buf, 1024, stdin)){ if(buf[strlen(buf) -1] == "\n") buf[strlen(buf) -1] = "\0"; write(soc, buf, 1024); read(soc, buf, 1024); fprintf(stdout, "%s\n", buf); } close(soc); return 0; } サーバー側プログラム #include <stdio.h> #include <stdlib.h> #include <ctype.h> #include <unistd.h> #include <sys/socket.h> #include <arpa/inet.h> #define SOCK_NAME "./socket" int main() { int i; int fd1, fd2; struct sockaddr_in saddr; struct sockaddr_in caddr; int len; int ret; char buf[1024]; if((fd1 =socket(AF_INET, SOCK_STREAM, 0)) < 0 ){ perror("socket"); exit(1); } memset((char *)&saddr, 0, sizeof(saddr)); saddr.sin_family = AF_INET; saddr.sin_addr.s_addr=INADDR_ANY; saddr.sin_port=htons(1357); unlink(SOCK_NAME); if(bind(fd1, (struct sockaddr *)&saddr, sizeof(saddr)) < 0) { perror("bind"); exit(1); } if(listen(fd1,5) < 0 ) { perror("listen"); exit(1); } while(1){ len = sizeof(caddr); if((fd2 = accept(fd1, (struct sockaddr *)&caddr, &len)) < 0){ perror("accept"); exit(1); } fprintf(stderr, "Connection established: socket %d used.\n", fd2); while((ret = read(fd2, buf, 1024)) > 0 ){ fprintf(stderr, "read: &s\n", buf); for(i=0; i<ret; i++) if(islower(buf[i])) buf[i] = toupper(buf[i]); if(isupper(buf[i])) buf[i] = tolower(buf[i]); fprintf(stderr, "write: %s\n", buf); write(fd2, buf, 1024); } close(fd2); } close(fd1); return 0; }

  • TCP/IP通信型電話番号検索プログラムを作りたいです。

    TCP/IP通信型電話番号検索プログラムを作りたいです。 クライアントは以下のようで大丈夫みたいなのですが、サーバの方を修正しなければなりません。 この質問で「TCP/IP通信型大文字・小文字変換プログラム」を発見しました。 サーバー側プログラム #include <stdio.h> #include <stdlib.h> #include <ctype.h> #include <unistd.h> #include <sys/socket.h> #include <arpa/inet.h> #define SOCK_NAME "./socket" int main() { int i; int fd1, fd2; struct sockaddr_in saddr; struct sockaddr_in caddr; int len; int ret; char buf[1024]; if((fd1 =socket(AF_INET, SOCK_STREAM, 0)) < 0 ){ perror("socket"); exit(1); } memset((char *)&saddr, 0, sizeof(saddr)); saddr.sin_family = AF_INET; saddr.sin_addr.s_addr=INADDR_ANY; saddr.sin_port=htons(1357); unlink(SOCK_NAME); if(bind(fd1, (struct sockaddr *)&saddr, sizeof(saddr)) < 0) { perror("bind"); exit(1); } if(listen(fd1,5) < 0 ) { perror("listen"); exit(1); } while(1){ len = sizeof(caddr); if((fd2 = accept(fd1, (struct sockaddr *)&caddr, &len)) < 0){ perror("accept"); exit(1); } fprintf(stderr, "Connection established: socket %d used.\n", fd2); while((ret = read(fd2, buf, 1024)) > 0 ){ fprintf(stderr, "read: &s\n", buf); for(i=0; i<ret; i++) if(islower(buf[i])) buf[i] = toupper(buf[i]); if(isupper(buf[i])) buf[i] = tolower(buf[i]); fprintf(stderr, "write: %s\n", buf); write(fd2, buf, 1024); } close(fd2); } close(fd1); return 0; } 先生によると、クライアントは同じもので良いそうです。 誰か、助けて下さい。

  • MessageBoxのことで聞きたいのですが…

    int i; int tmphyoukachi[KYOKU_SHUDAN]; bool cancel_flag; cancel_flag = false; ~~~~~~~~~ /*ユーザー評価(ダイアログでYES・NO)*/ int Rslt; Rslt = MessageBox(NULL, "", "",MB_YESNOCANCEL); if (Rslt == (IDYES)){ //Rslt = MessageBox(NULL, "YES","",MB_OK); kyoku[i][0] += 50000; } else if(Rslt == (IDNO)){ kyoku[i][0] -= 50000; }else if(Rslt == (IDCANCEL)){ cancel_flag = true; } mciSendString("close MIDIFILE",NULL,0,NULL); if(cancel_flag == true){ break; } } return cancel_flag; というような遺伝的アルゴリズムを用いて自動作曲システムを作りました。これはプログラムの一部なんですが、MessageBoxでカウントして何回目で終了というようなプログラムを作成したいのですが、どなたか分かるかたがいらっしゃいましたよろしくお願いします。

  • SSL_connect(ssl)

    お世話になっています。 VC++2005、MFC、Win7、openssl で作業しています。 Gメールから、POP3S 接続でメールを受け取りたいと考えています。 メールヘッダーの受信後に、本文を取り出す前に接続が切れます。 最初に、接続の部分ですが、問題点がありましたら、アドバイスをください。 void CSQMailBoxTreeView::GmailMailDL(){ int nReturnCode; WSADATA wsaData; CFileException fileExpection; #define MAJOR_VERSION_REQUIRED 1 #define MINOR_VERSION_REQUIRED 1 struct sockaddr_in server; std::string req; // リクエスト std::string res; // レスポンス std::string host_url = "pop.googlemail.com"; strcpy_s(gszGmailServerName,(LPCTSTR)oc_Gmailpop3servername); if(strlen(gszGmailServerName)==0){ MessageBox("設定 - Gmail POP3サーバー から、\n受信メール(POP3)サーバを\n入力して下さい。","POP Server", MB_OK); } strcpy_s(gszGmailUserId, (LPCTSTR)oc_Gmailpop3userid); if(strlen(gszGmailUserId)==0){ MessageBox("設定 - Gmail POP3サーバー から、\nメールサーバのユーザ名を\n入力してください。","POP User ID", MB_OK); } strcpy_s(gszGmailPassword, (LPCTSTR)oc_Gmailpop3password); if(strlen(gszGmailPassword)==0){ MessageBox("設定 - Gmail POP3サーバー から、\nパスワードを入力してください。","警告 PassWord", MB_OK); } strcpy_s(gszGmailPOP3Port, (LPCTSTR)oc_Gmailpop3port); if(strlen(gszGmailPassword)==0){ MessageBox("設定 - Gmail POP3サーバー から、\nポート番号を入力してください。","POP3 PortNumber", MB_OK); } // Prepare version for WSAStartup() WORD wVersionRequired = MAKEWORD(MAJOR_VERSION_REQUIRED, MINOR_VERSION_REQUIRED); // Initialize the WinSock DLL nReturnCode = WSAStartup(wVersionRequired, &wsaData); if (nReturnCode != 0 ){ MessageBox("Error on WSAStartup()", "CheckGMail", MB_OK); return ; } // Confirm that the version requested is available. if (wsaData.wVersion != wVersionRequired){ // Version needed is not available. MessageBox("Wrong WinSock Version", "CheckGMail", MB_OK); WSACleanup(); return ; } sock = socket(AF_INET, SOCK_STREAM, 0); server.sin_family = AF_INET; server.sin_port = htons(995); server.sin_addr.S_un.S_addr = inet_addr(host_url.c_str()); if (server.sin_addr.S_un.S_addr == 0xffffffff) { struct hostent *host; unsigned int **addrptr; host = gethostbyname(host_url.c_str()); if (host == NULL) { return ; } addrptr = (unsigned int **)host->h_addr_list; while (*addrptr != NULL) { server.sin_addr.S_un.S_addr = *(*addrptr); if (connect(sock, (struct sockaddr *)&server, sizeof(server)) == 0) { break; } } if (*addrptr == NULL) { sprintf_s(outbuf3, "Fatal error: unable to connect to the server.\n"); MessageBox(outbuf3,"Error", MB_OK); WSACleanup(); return;// -1; } } else { if (connect(sock, (struct sockaddr *)&server, sizeof(server)) != 0){ return ; } } SSL_load_error_strings(); SSL_library_init(); ctx = SSL_CTX_new(TLSv1_method()); if (ctx == NULL) { return;// 1; } ssl = SSL_new(ctx); if (ssl == NULL) { return;// 1; } if (SSL_set_fd(ssl, sock) == 0) { return;// 1; } RAND_poll(); while (RAND_status() == 0) { unsigned short rand_ret = rand() % 65536; RAND_seed(&rand_ret, sizeof(rand_ret)); } int ev = SSL_connect(ssl); if ( ev != 1) { int ret = SSL_get_error(ssl, ev); if(ret <= 0){ ERR_print_errors_fp(stderr); return;// 1; } } if (WSAAsyncSelect(sock, *this, SM_GASYNC3, FD_CONNECT|FD_READ|FD_WRITE|FD_CLOSE) == SOCKET_ERROR){ MessageBox("WSAAsyncSelect() failed","Error", MB_OK); closesocket(sock); sock = INVALID_SOCKET; return; } gnAppState = STATE_CONNECTING; }

  • 今DirectSoundの初期化でわからないことがあります。カレントデ

    今DirectSoundの初期化でわからないことがあります。カレントディレクトリにもsoundファイルにもwavファイルがあるのにうまく読み込まれません。また、mmioRead関数でなぜか失敗時の処理が出てしまいます。下に一部省略したソースを書きます。 if(FAILED(hr = OpenWaveFile(aWaveFileName, aSound))) { TCHAR strWavFile[MAX_PATH]; TCHAR kSoundsPath[6]={'s','o','u','n','d','/'}; int kSoundsPathLength=6; lstrcpyn(strWavFile, kSoundsPath, MAX_PATH); lstrcpyn(strWavFile + kSoundsPathLength, aWaveFileName, MAX_PATH - kSoundsPathLength); if(FAILED(hr = OpenWaveFile((LPSTR)strWavFile, aSound))) { sprintf(tmpString, "wavファイル『%s』が見つかりませんでした", strWavFile); goto FAIL_RETURN; } HRESULT Sound::OpenWaveFile(LPSTR aWaveFileName, theSounds *aSound) { mmioOpen→mmioDescend →aChunkInfo.ckid = mmioFOURCC('f', 'm', 't', ' '); if(MMSYSERR_NOERROR != mmioDescend(aSound->sndHmmio, &aChunkInfo, &(aSound->sndChunkRiff), MMIO_FINDCHUNK)) { MessageBox(NULL, "FAIL:mmioDescend2","エラー", MB_OK | MB_ICONHAND); CloseWaveFile(aSound); return(E_FAIL); } →if(mmioRead(aSound->sndHmmio, (HPSTR) &aPCMWaveFormat, sizeof(aPCMWaveFormat)) != sizeof(aPCMWaveFormat)) { MessageBox(NULL, "FAIL:mmioRead","エラー", MB_OK | MB_ICONHAND); CloseWaveFile(aSound); return (E_FAIL); } } ソースは以上です。誰か原因に心当たりがある方がいましたら回答お願いします。

専門家に質問してみよう