[소켓]윈도우 서버, 리눅스 클라이언트..
글쓴이: sdlb / 작성시간: 토, 2014/07/26 - 3:00오후
윈도우에서 소켓서버를 열고 리눅스 클라이언트가 서버에게 파일을 전송하는 프로그램인데요.. 자꾸 리눅스 connect에서 에러가 납니다..
윈도우 서버 소켓소스 입니다.
#pragma comment(lib,"ws2_32") #include <stdio.h> #include <stdlib.h> #include <winsock2.h> void ErrorHandling(char* message); int main(int argc, char** argv) { WSADATA wsaData; // 초기화 할때 쓰려고 선언했습니다. // SOCKET hServSock, hClntSock; SOCKADDR_IN servAddr, clntAddr; char revbuf[LENGTH]; // Receiver buffer int success = 0; int szClntAddr; if (argc != 2) { // 포트정보가 입력되었는지 여부 검사 // printf("Usage : %s <port>\n", argv[0]); exit(1); } // 윈속 2.2사용 초기화 // if (WSAStartup(MAKEWORD(2, 2), &wsaData) != 0) // Error check // ErrorHandling("WSAStartup() error!"); else printf("[Server] Winsock2.2 Configuring is successfully\n"); // 소켓을 생성합니다. // hServSock = socket(AF_INET, SOCK_STREAM, 0); // TCP socket // if (hServSock == INVALID_SOCKET) ErrorHandling("socket() error"); else printf("[Server] Creating socket successfully\n"); memset(&servAddr, 0, sizeof(servAddr)); servAddr.sin_family = AF_INET; // TCP를 사용합니다. // servAddr.sin_addr.s_addr = htonl(INADDR_ANY); // 모든 IP를 받아줍니다. // servAddr.sin_port = htons(atoi(argv[1])); // 포트 정보 // // host to network short if (bind(hServSock, (SOCKADDR*)&servAddr, sizeof(servAddr)) == SOCKET_ERROR) // 소켓에 주소를 부여합니다. // ErrorHandling("bind() error"); else printf("[Server] Binded tcp port %d in addr host successfully.\n", PORT); if (listen(hServSock, 10) == SOCKET_ERROR) // 소켓대기상태로 만듭니다, 동시에 10명까지 가능합니다. // ErrorHandling("listen() error"); else printf("[Server] Listening the port %d successfully.\n", PORT); while (success == 0) { szClntAddr = sizeof(SOCKADDR_IN); /* Wait a connection, and obtain a new socket file despriptor for single connection */ if ((hClntSock = accept(hServSock, (SOCKADDR*)&clntAddr, &szClntAddr)) == SOCKET_ERROR) { fprintf(stderr, "ERROR: Obtaining new Socket Despcritor. (errno = %d)\n", errno); exit(1); } else printf("[Server] Server has got connected from Clinet.\n");// inet_ntoa(addr_remote.sin_addr)); /* Receive File from Client(show console) */ //int fr_block_sz = 0; //while ((fr_block_sz = recv(hClntSock, revbuf, LENGTH, 0)) > 0) //{ // printf(revbuf); //} /* Receive File from Client(save text) */ char* fr_name = "C:\\receive.txt"; FILE *fr; fr = fopen(fr_name, "a"); if (fr == NULL) printf("File %s Cannot be opened file on server.\n", fr_name); else { memset(revbuf, LENGTH, '0'); int fr_block_sz = 0; while ((fr_block_sz = recv(hClntSock, revbuf, LENGTH, 0)) > 0) { int write_sz = fwrite(revbuf, sizeof(char), fr_block_sz, fr); if (write_sz < fr_block_sz) { ErrorHandling("File write failed on server.\n"); } memset(revbuf, LENGTH, '0'); if (fr_block_sz == 0 || fr_block_sz != 1024) { break; } } } } return 0; } void ErrorHandling(char* message) { fputs(message, stderr); fputc('\n', stderr); exit(1); }
리눅스 클라이언트소켓소스 입니다.
#include <stdlib.h> #include <stdio.h> #include <errno.h> #include <string.h> #include <sys/types.h> #include <netinet/in.h> #include <sys/wait.h> #include <sys/socket.h> #include <signal.h> #include <ctype.h> #include <arpa/inet.h> #include <netdb.h> #define PORT 20000 #define LENGTH 512 void error(const char *msg) { perror(msg); exit(1); } int main(int argc, char *argv[]) { /* Variable Definition */ int sockfd; int nsockfd; char revbuf[LENGTH]; struct sockaddr_in remote_addr; /* Get the Socket file descriptor */ if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1) { fprintf(stderr, "ERROR: Failed to obtain Socket Descriptor! (errno = %d)\n",errno); exit(1); } /* Fill the socket address struct */ remote_addr.sin_family = AF_INET; remote_addr.sin_port = htons(PORT); inet_pton(AF_INET, "127.0.0.1", &remote_addr.sin_addr); bzero(&(remote_addr.sin_zero), 8); /* Try to connect the remote */ if (connect(sockfd, (struct sockaddr *)&remote_addr, sizeof(struct sockaddr)) == -1) { fprintf(stderr, "ERROR: Failed to connect to the host! (errno = %d)\n",errno); <<<<<< 실행시 이쪽 에러가 발생됩니다. exit(1); } else printf("[Client] Connected to server at port %d...ok!\n", PORT); char* fs_name = "/home/aryan/Desktop/quotidiani.txt"; char sdbuf[LENGTH]; printf("[Client] Sending %s to the Server... ", fs_name); FILE *fs = fopen(fs_name, "r"); if(fs == NULL) { printf("ERROR: File %s not found.\n", fs_name); exit(1); } bzero(sdbuf, LENGTH); int fs_block_sz; while((fs_block_sz = fread(sdbuf, sizeof(char), LENGTH, fs)) > 0) { if(send(sockfd, sdbuf, fs_block_sz, 0) < 0) { fprintf(stderr, "ERROR: Failed to send file %s. (errno = %d)\n", fs_name, errno); break; } bzero(sdbuf, LENGTH); } printf("Ok File %s from Client was Sent!\n", fs_name); close (sockfd); printf("[Client] Connection lost.\n"); return (0); }
윈도우 서버는 잘 돌아갑니다. 윈도우서버&윈도우클라이언트로 실행할때는 잘 되는데 리눅스 클라이언트로 실행할때에 connect부분에서 에러가 나더군요..
고민 고민하다가 클라이언트 쪽을 tcpdump로 찍어본 결과 클라이언트의 seq 패킷은 서버쪽ip:port로 잘 갑니다. 제 생각엔 문제는 서버쪽 accept 같은데 무슨 문제일까요.. 반나절 해보다가 가르침을 받고싶어 게시판에 올려봅니다.
Forums:
Connect to 127.0.0.1 ??
inet_pton(AF_INET, "127.0.0.1", &remote_addr.sin_addr);
음
음 inet_pton(AF_INET,"127.0.0.1",&remote_aadr.sin_addr); 바꿨는데 안되네용 ㅎ
리눅스 서버 문제가 아닐련지요
iptables 같은 방화벽이 켜져있다거나
리눅스쪽 ip가 제대로 안잡혀있다거나요.
윈도우나 리눅스나 소스쪽엔 별다른 문제가 없어보이는군요.
검증된 프로그램으로 한번 해보세요.
윈도용 FTP서버라든지 http 파일서버라든지 등등.. 포터블 형태로 되어 있는 것도 많으니, 그중에 아무거나 가져다가 테스트를 원하는 포트 번호를 넣고 실행 후 리눅스에서 접속해보면 바로 알 수 있겠죠. 환경 문제인지 프로그램 오류인지 말이죠.
--
댓글 달기