Linux下Socket编程 怎样实现客户端之间互相通信

Linux下Socket编程 怎样实现客户端之间互相通信,第1张

网络的Socket数据传输是一种特殊的I/O,Socket也是一种文件描述符。Socket也具有一个类似于打开文件的函数调用Socket(),该函数返回一个整型的Socket描述符,随后的连接建立、数据传输等 *** 作都是通过该Socket实现的。

下面用Socket实现一个windows下的c语言socket通信例子,这里我们客户端传递一个字符串,服务器端进行接收。

【服务器端】

#include "stdafx.h"

#include <stdio.h>

#include <winsock2.h>

#include <winsock2.h>

#define SERVER_PORT 5208 //侦听端口

void main()

{

    WORD wVersionRequested

    WSADATA wsaData

    int ret, nLeft, length

    SOCKET sListen, sServer //侦听套接字,连接套接字

    struct sockaddr_in saServer, saClient //地址信息   

    char *ptr//用于遍历信息的指针   

    //WinSock初始化

    wVersionRequested=MAKEWORD(2, 2) //希望使用的WinSock DLL 的版本

    ret=WSAStartup(wVersionRequested, &wsaData)

    if(ret!=0)

    {

        printf("WSAStartup() failed!\n")

        return

    }

    //创建Socket,使用TCP协议

    sListen=socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)

    if (sListen == INVALID_SOCKET)

    {

        WSACleanup()

        printf("socket() faild!\n")

        return

    }

    //构建本地地址信息

    saServer.sin_family = AF_INET //地址家族

    saServer.sin_port = htons(SERVER_PORT) //注意转化为网络字节序

    saServer.sin_addr.S_un.S_addr = htonl(INADDR_ANY) //使用INADDR_ANY 指示任意地址

  

    //绑定

    ret = bind(sListen, (struct sockaddr *)&saServer, sizeof(saServer))

    if (ret == SOCKET_ERROR)

    {

        printf("bind() faild! code:%d\n", WSAGetLastError())

        closesocket(sListen) //关闭套接字

        WSACleanup()

        return

    }

  

    //侦听连接请求

    ret = listen(sListen, 5)

    if (ret == SOCKET_ERROR)

    {

        printf("listen() faild! code:%d\n", WSAGetLastError())

        closesocket(sListen) //关闭套接字

        return

    }

  

    printf("Waiting for client connecting!\n")

    printf("Tips: Ctrl+c to quit!\n")

    //阻塞等待接受客户端连接

 while(1)//循环监听客户端,永远不停止,所以,在本项目中,我们没有心跳包。

 {

  length = sizeof(saClient)

  sServer = accept(sListen, (struct sockaddr *)&saClient, &length)

  if (sServer == INVALID_SOCKET)

  {

   printf("accept() faild! code:%d\n", WSAGetLastError())

   closesocket(sListen) //关闭套接字

   WSACleanup()

   return

  }       

  char receiveMessage[5000]

   nLeft = sizeof(receiveMessage)

  ptr = (char *)&receiveMessage

  while(nLeft>0)

  {

   //接收数据

   ret = recv(sServer, ptr, 5000, 0)

   if (ret == SOCKET_ERROR)

   {

    printf("recv() failed!\n")

    return

   }

   if (ret == 0) //客户端已经关闭连接

   {

    printf("Client has closed the connection\n")

    break

   }

   nLeft -= ret

   ptr += ret

  }  

    printf("receive message:%s\n", receiveMessage)//打印我们接收到的消息。

  

 }

  //  closesocket(sListen)

  //  closesocket(sServer)

  //  WSACleanup()

}

【客户端】

#include "stdafx.h"

#include <stdio.h>

#include <stdlib.h>

#include <winsock2.h>

#define SERVER_PORT 5208 //侦听端口

void main()

{

   WORD wVersionRequested

   WSADATA wsaData

   int ret

   SOCKET sClient //连接套接字

   struct sockaddr_in saServer //地址信息

   char *ptr

   BOOL fSuccess = TRUE

   //WinSock初始化

   wVersionRequested = MAKEWORD(2, 2) //希望使用的WinSock DLL的版本

   ret = WSAStartup(wVersionRequested, &wsaData)

   if(ret!=0)

   {

        printf("WSAStartup() failed!\n")

        return

   }

   //确认WinSock DLL支持版本2.2

   if(LOBYTE(wsaData.wVersion)!=2 || HIBYTE(wsaData.wVersion)!=2)

   {

        WSACleanup()

        printf("Invalid WinSock version!\n")

        return

   }

   //创建Socket,使用TCP协议

   sClient = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)

   if (sClient == INVALID_SOCKET)

   {

        WSACleanup()

        printf("socket() failed!\n")

        return

   }

   //构建服务器地址信息

   saServer.sin_family = AF_INET //地址家族

   saServer.sin_port = htons(SERVER_PORT) //注意转化为网络节序

   saServer.sin_addr.S_un.S_addr = inet_addr("192.168.1.127")

   //连接服务器

   ret = connect(sClient, (struct sockaddr *)&saServer, sizeof(saServer))

   if (ret == SOCKET_ERROR)

   {

        printf("connect() failed!\n")

        closesocket(sClient) //关闭套接字

        WSACleanup()

        return

   }

  

  

   char sendMessage[]="hello this is client message!"

   ret = send (sClient, (char *)&sendMessage, sizeof(sendMessage), 0)

   if (ret == SOCKET_ERROR)

   {

        printf("send() failed!\n")

   }

   else

        printf("client info has been sent!")

   closesocket(sClient) //关闭套接字

   WSACleanup()

}

请终端下输入

sudo netstat -a

如果看到了,如果能看到很多unix的链接流。则证明linux系统本身已经启用了很多socket通信。已经是设置好的。

至于如何进行socket通信编程。请寻找相关资料自学。

如果你只是想建立到远端服务器的一个ip隧道。架设加密代理的隧道,那么请告知你使用的linux版本,以及使用的软件。

Socket通信创建步骤:

(1)通过socket()函数创建socket

(2)通过bind函数绑定socket于设备地址

(3)进行读写 *** 作read/recv/recvfrom write/send/sendto

(4)close方法关闭套接字

例子如下:

test1.c

#include <stdio.h>  

#include <stdlib.h>  

#include <unistd.h>  

#include <netinet/in.h>  

#include <arpa/inet.h>  

  

int main(void)  

{  

    //create socket  

    int fd = socket(AF_INET, SOCK_DGRAM, 0)  

    if(fd==-1)  

    {  

        perror("socket\n")  

        exit(-1)  

    }  

    printf("socket fd=%d\n",fd)  

  

    //build connection address  

    struct sockaddr_in addr  

    addr.sin_family = AF_INET  

    addr.sin_port = htons(6666)  

    addr.sin_addr.s_addr = inet_addr("127.0.0.1")  

  

    int r  

    r = bind(fd,(struct sockaddr*)&addr,sizeof(addr))  

    if(r==-1)  

    {  

        perror("bind")  

        close(fd)  

        exit(-1)  

    }  

    printf("bind address successful!\n")  

    //accept or send message  

    char buf[255]  

    struct sockaddr_in from  

    socklen_t len  

    len = sizeof(from)  

    while(1)  

    {  

        r = recvfrom(fd,buf,sizeof(buf)-1,0,(struct sockaddr*)&from,&len)  

        if(r>0)  

        {  

            buf[r]=0  

            printf("The message from %s is:%s\n",inet_ntoa(from.sin_addr),buf)  

        }  

        else  

        {  

            break  

        }  

    }  

    //close socket  

    close(fd)  

    return 0  

}

test2.c

#include <stdio.h>  

#include <stdlib.h>  

#include <unistd.h>  

#include <string.h>  

#include <sys/socket.h>  

#include <netinet/in.h>  

#include <arpa/inet.h>  

  

int main(void)  

{  

    //create socket  

    int fd = socket(AF_INET,SOCK_DGRAM,0)  

    if(fd==-1)  

    {  

        perror("socket")  

        exit(-1)  

    }  

    printf("create socket OK!\n")  

    //create an send address  

    struct sockaddr_in addr={}  

    addr.sin_family = AF_INET  

    addr.sin_port = htons(6666)  

    addr.sin_addr.s_addr=inet_addr("127.0.0.1")  

    //send the message to the specify address  

    int r  

    char buf[255]  

    while(1)  

    {  

        r = read(0,buf,sizeof(buf)-1)  

        if(r<=0)  

            break  

        sendto(fd,buf,r,0,(struct sockaddr*)&addr,sizeof(addr))  

    }  

    //close socket  

    close(fd)  

    return 0  

}

先运行test1.c,然后运行test2.c,在test2.c运行后输入内容,在test1.c所在终端中就会显示信息

运行结果如下:


欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/yw/8457620.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-04-16
下一篇 2023-04-16

发表评论

登录后才能评论

评论列表(0条)

保存