如何使用 recv 逐行阅读 html 页?

How can i read html page line by line using recv?

我尝试用C语言练习socket编程
我试图做的是逐行阅读某些 html 页,这意味着一直读到 '\n'。
但是,问题是由于 recv 的属性读取一定长度,我们将其作为参数传递给 recv() 的第三个参数。
例如,

char buff[256];
.
.
recv(socknumber, buf, sizeof(buff), 0);

在这种情况下,recv 读取的字符串与 sizeof(buff) 一样多。所以我不知道如何处理 '\n'

由于我是C处女,请给我一些提示,或者简单的代码。谢谢

socket传输没有线路的概念,需要自己实现。即使在 SO 中也有很多解决方案,请参阅那个 read line by line from a socket buffer。您还可以从套接字描述符中获取 FILE 句柄并使用 *gets 函数(如果您使用的是 Unix,请查看 fdopen)。

没有 standard 实现您的要求。你需要做的是有一个合适的 sending 和一个 receiving 套接字程序。

一个建议方法:

  • Sender 逐块读取 HTML 文件(假设每次读取 100 个字节)并将它们发送到 reciever
  • Receiver 接受发送方发送的数据块并写入文件。 (接收方知道块的大小)
  • 您可以在开始传输前指定文件长度。

您需要什么:

此外:这是我的示例代码集

"Client 按名称请求文件和 server 响应文件(如果可用)逐块请求"=22=]

服务器:

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

#define TRUE 1
#define FALSE 0
#define SIZE 1024


int main(int argc, char**argv)
{
    /*Variable set*/
    int listenfd,connfd,n,size;
    FILE * ff;
    struct sockaddr_in servaddr,cliaddr;
    socklen_t clilen;
    char buffer[SIZE];

    /* Dedicated socket to listening */
    listenfd=socket(AF_INET,SOCK_STREAM,0);

    /* Initialize a sockaddr_in struct with our own address information for binding the socket */
    servaddr.sin_family = AF_INET;
    servaddr.sin_addr.s_addr=htonl(INADDR_ANY);
    servaddr.sin_port=htons(32000);

    /* Binding */
    bind(listenfd,(struct sockaddr *)&servaddr,sizeof(servaddr));

    /*Listening to the socket*/
    listen(listenfd,0);
    clilen=sizeof(cliaddr);

    /*Wait till a client request a file*/
    connfd = accept(listenfd,(struct sockaddr *)&cliaddr,&clilen); // the uninitialized cliaddr variable is filled in with the
    n = recvfrom(connfd,buffer,SIZE ,0,(struct sockaddr *)&cliaddr,&clilen);// information of the client by recvfrom function
    buffer[n] = '[=10=]';

    printf("CLient requested %s:\n",buffer);

    /*Trying to open requested file*/
    ff=fopen(buffer,"r");
    if(ff==NULL){
        printf("Request file not found..!!\n");
        strcpy(buffer,"NACK");
        sendto(connfd,buffer,sizeof(buffer),0,(struct sockaddr *)&cliaddr,sizeof(cliaddr)); 
        return(0); //exit
    }

    /*If file is availbe - Find the size of file*/
    fseek(ff,0L,SEEK_END);
    size=ftell(ff);

    fseek(ff,0L,SEEK_SET);
    sprintf(buffer,"%d",size);

    /*Send size of file*/
    sendto(connfd,buffer,sizeof(buffer),0,(struct sockaddr *)&cliaddr,sizeof(cliaddr));


    /*Sits in a loop and send 1000 byte chunks -Uppon ACK's from client*/

    int i;
    int t=TRUE;
    char c;

    while(t){

        /*Recieve client flag*/
        n = recvfrom(connfd,buffer,SIZE,0,(struct sockaddr *)&cliaddr,&clilen);
        buffer[n] = 0;

        /*If its not ACK then exit*/
        if(strcmp(buffer,"ACK")){
            printf("CLient failled to grab data chunks..\n");
            return(0);
        }

        /*Else read 1000 bytes*/
        for(i=0;i<1000;i++){
            c=fgetc(ff);
            buffer[i]=c;
            if(c==EOF){
                t=FALSE;
                break;
            }
        }

        /*Send red data chunk*/
        sendto(connfd,buffer,i,0,(struct sockaddr *)&cliaddr,sizeof(cliaddr));
        printf("Sending.. %d bytes \n",i);
    }

    /*Close file*/
    fclose(ff);


    return 0;
}

客户:

#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>


/*Macros*/
#define SIZE 1024
#define TRUE 1

int main(int argc, char**argv)
{
    /*Variable Set*/
    int sockfd,n,len;
    FILE * ff;
    struct sockaddr_in servaddr;
    char buffer[SIZE];

    if (argc != 2)
    {
        printf("usage:  ./%s <IP address>\n",argv[0]);
        return -1;
    }
    /* socket to connect */
    sockfd=socket(AF_INET,SOCK_STREAM,0);

    /* IP address information of the server to connect to */ 
    servaddr.sin_family = AF_INET;
    servaddr.sin_addr.s_addr=inet_addr(argv[1]);
    servaddr.sin_port=htons(32000);

    connect(sockfd, (struct sockaddr *)&servaddr, sizeof(servaddr));

    /*Ask user to specify required file name*/
    printf("What's the required file ? ");
    scanf("%s",buffer);

    /*Send requested file name to server*/
    sendto(sockfd,buffer,SIZE,0, (struct sockaddr *)&servaddr,sizeof(servaddr));
    n=recvfrom(sockfd,buffer,SIZE,0,NULL,NULL);
    buffer[n]=0;

    /*If server found that file is not present it sends a NACK*/
    if(!strcmp(buffer,"NACK")){
        printf("Required file not in server..\n");
        return(1);
    }

    /*Else server send the size of the file*/
    printf("FIle size is %s bytes \n",buffer);
    len=atoi(buffer);

    /* Open/create file to save recieved data*/
    ff=fopen("clientfile.txt","w"); /*OPen or create the file to be written*/

    /*Check for file creation success*/
    if(ff==NULL){
        strcpy(buffer,"NACK");
        sendto(sockfd,buffer,SIZE,0, (struct sockaddr *)&servaddr,sizeof(servaddr));
        printf("File creating failled.. \n");
        return(0);
    }


    /*Client stays in a loop till it recieve full data*/
    int c=0;
    while(c<len){

        /*Each time client sends ACK to recieve next data chunk*/
        strcpy(buffer,"ACK");
        sendto(sockfd,buffer,SIZE,0, (struct sockaddr *)&servaddr,sizeof(servaddr));

        n=recvfrom(sockfd,buffer,sizeof(buffer),0,NULL,NULL);
        printf("Recieved %d bytes\n",n);

        /*Increase counter by recieve chunk size*/
        c+=n;

        /*Add null character to end of data*/
        if(c>=len){
            buffer[n]='[=11=]';
        }

        /*Append to file*/
        fwrite(buffer,sizeof(char),n,ff);
    }

    fclose(ff);
    printf("File sucessfully recieved..\n");
    return 0;
}