Linux下的类似QQ聊天程序

想在Linux下用socket套接字写个类似于windows下的QQ聊天程序,但是遇到不能循环发送和接受的问题,希望能向各位大侠请教,以下是代码:

这是server端代码:

 #include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include<errno.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<netinet/in.h>

int main()
{
        int oldfd,newfd;
        struct sockaddr_in mysock;
        int n;
        char buf[1024];

        oldfd=socket(AF_INET,SOCK_STREAM,0);
        memset(&mysock,0,sizeof(mysock));
        mysock.sin_family=AF_INET;
        mysock.sin_port=htons(1025);
        mysock.sin_addr.s_addr=htonl(INADDR_ANY);

        bind(oldfd,(struct sockaddr*)&mysock,sizeof(mysock));
        listen(oldfd,13);
        while(1)
        {
                newfd=accept(oldfd,(struct sockaddr*)NULL,NULL);
                //read();
                n=read(newfd,buf,sizeof(buf));
                buf[n]=0;
                printf("%s\n",buf);
                write(newfd,buf,n);//再写到client上去
                close(newfd);
            }
        close(oldfd);
        return 0;
    }


以下是client端的代码:

 #include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include<errno.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<netinet/in.h>
#include<unistd.h>

int main(int argc,char **argv)
{
    int fd;
    int n;
    struct sockaddr_in mysock;
    char buf[1024];

    fd=socket(AF_INET,SOCK_STREAM,0);
    memset(&mysock,0,sizeof(mysock));
    mysock.sin_family=AF_INET;
    mysock.sin_port=htons(1025);
    inet_pton(AF_INET,argv[1],&mysock.sin_addr.s_addr);
    while(1){//这是在一次连接成功后添加的循环
        connect(fd,(struct sockaddr*)&mysock,sizeof(mysock));
        n=read(STDIN_FILENO,buf,sizeof(buf));
        write(fd,buf,n);

        read(fd,buf,sizeof(buf));
        buf[n]=0;
        printf("this is fankui information:%s\n",buf);

    }
    close(fd);
    return 0;
    }


3个回答

I assume you can make sense of my code!
so i just show you code below,if you have any question,
just let me know !!1

server.c

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <unistd.h>

#define BUF_SIZE 1024
#define LISTEN_PORT 8889
#define LISTEN_NO 10
#define err_exit(msg) (perror(msg),(exit(EXIT_FAILURE)))

int sock_make(void);
void read_from(int fd);
void send_to(int fd);

int main(void)
{
    int sockfd,connfd;
    struct sockaddr_in clientaddr;
    int n;
    char buf[BUF_SIZE];
    char recvbuf[BUF_SIZE];
    char sendbuf[BUF_SIZE];


    sockfd=sock_make();
    while(1){
        //If you wanna know which client and what the ip is 
        //You should no set the the argu being NULL ..

        if((connfd=accept(sockfd,(struct sockaddr*)NULL,NULL))<0)
        {
            err_exit(">>accept");
        }else{
            while(1){
                puts("-----------wait message---------");
KEEP_READ:
                n=read(connfd,recvbuf,sizeof(recvbuf));
                //recvbuf[n]=0;
                printf("%s\n",recvbuf);
                if(strncmp(recvbuf,".",1)) goto KEEP_READ;
                puts("-----------Please input----------");
KEEP_SEND:
                n=read(STDIN_FILENO,sendbuf,sizeof(sendbuf));
                sendbuf[n]=0;
                write(connfd,sendbuf,sizeof(sendbuf));
                if(strncmp(sendbuf,".",1)) goto KEEP_SEND;

            }
            close(connfd);
        }
    }
    close(sockfd);
    return 0;
}
int sock_make(void)
{
    struct sockaddr_in clientaddr;
    int sockfd;
    memset(&clientaddr,SOCK_STREAM,sizeof(clientaddr));
    clientaddr.sin_family=AF_INET;
    clientaddr.sin_port=htons(LISTEN_PORT);
    clientaddr.sin_addr.s_addr=htonl(INADDR_ANY);

    if((sockfd=socket(AF_INET,SOCK_STREAM,0))<0)
    {
        err_exit(">>socket");
    }

    if(bind(sockfd,(struct sockaddr*)&clientaddr,sizeof(clientaddr))<0)
    {
        err_exit(">>bind");
    }

    listen(sockfd,LISTEN_NO);

    return sockfd;
}


client.c

 #include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <unistd.h>


#define BUF_SIZE 1024
#define LISTEN_PORT 8889
#define LISTEN_NO 10
#define err_exit(msg) (perror(msg),(exit(EXIT_FAILURE)))

int main(int argc,char * argv[])
{
    int sockfd;
    int n;
    struct sockaddr_in serverAddr;
    char sendbuf[BUF_SIZE];
    char recvbuf[BUF_SIZE];

    if((sockfd=socket(PF_INET,SOCK_STREAM,0))<0)
    {   
        err_exit(">>socket");
    }   
    memset(&serverAddr,0,sizeof(serverAddr));

    serverAddr.sin_family=AF_INET;

    serverAddr.sin_port=htons(LISTEN_PORT);
    inet_pton(PF_INET,argv[1],&serverAddr.sin_addr.s_addr);

    while(1)
    {   
        if((connect(sockfd,(struct sockaddr*)&serverAddr,sizeof(serverAddr)))<0)
        {
            err_exit(">>connect");
        }else{
            while(1){

                puts("--------------Please input-----------");
KEEP_SEND:
                n=read(STDIN_FILENO,sendbuf,sizeof(sendbuf));
                sendbuf[n]=0;
                write(sockfd,sendbuf,sizeof(sendbuf));
                if(strncmp(sendbuf,".",1)) goto KEEP_SEND;
                puts("-------------Wait message------------");
KEEP_READ:
                n=read(sockfd,recvbuf,sizeof(recvbuf));
                //recvbuf[n]=0; //EOF ..
                printf("%s\n",recvbuf);
                if(strncmp(recvbuf,".",1)) goto KEEP_READ;
            }
            close(sockfd);
        }
    }   
    return 0;
}


Please ,run the client as :

 ./client 127.0.0.1 

if you run the both on both terminal
and you see something below:

terminal 1 (run server)

 landpack@landpack-VirtualBox:~/ak/csdn$ ./server
-----------wait message---------
hello

I am Landpack

.

-----------Please input----------
Hey Landpack !
good to know you
.
-----------wait message---------

terminal 2 (run client)

 landpack@landpack-VirtualBox:~/ak/csdn$ ./client 127.0.0.1
--------------Please input-----------
hello
I am Landpack
.
-------------Wait message------------
Hey Landpack !

good to know you

.

--------------Please input-----------


All suggestion are welcome !
Have fun !!

u011767611
Landpack Please input a dot (".") when stop client send,and then ,the client will wait message ...
大约 5 年之前 回复
qnmd123
容成子 server端发送到client端怎么不行呢?
大约 5 年之前 回复

这里有个完整的例子,你可以参考哦
http://download.csdn.net/detail/luofenglian/4766630
如果有帮助,就请您采纳下我的回答吧,捂脸~~

qnmd123
容成子 而且只要C代码编写的
大约 5 年之前 回复
qnmd123
容成子 要求最简单的收发啊,姐姐;就是互相发送接受字符串的
大约 5 年之前 回复

connect成功后就可以循环发送数据。不用connect放到whilr循环中

Csdn user default icon
上传中...
上传图片
插入图片
抄袭、复制答案,以达到刷声望分或其他目的的行为,在CSDN问答是严格禁止的,一经发现立刻封号。是时候展现真正的技术了!
立即提问
相关内容推荐