首页 > 解决方案 > 发送日期和时间作为 TCP 服务器欢迎消息

问题描述

我必须插入这段代码:

time_t ticks = time(NULL);
snprintf(buff, sizeof(buff), "%.24s\r\n", ctime(&ticks));

将某人连接到服务器时显示的消息从“Hello student!\n”更改为当前时间和日期,但我不知道在程序中将这两行代码复制到哪里以及我必须修改什么复制这两行后的代码。

#include <stdio.h>      
#include <sys/types.h>
#include <sys/socket.h>   
#include <netdb.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <time.h> 

const char MESSAGE[] = "Hello student!\n";

int main(int argc, char *argv[]) {
    int simpleSocket = 0;
    int simplePort = 0;
    int returnStatus = 0;
    struct sockaddr_in simpleServer;
    
    if (argc != 2) {
        fprintf(stderr, "Usage: %s <port>\n", argv[0]);
        exit(1);
    }

    simpleSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);

    if (simpleSocket == -1) {
        fprintf(stderr, "Could not create a socket!\n");
        exit(1);
    }
    else {
        fprintf(stderr, "Socket created!\n");
    }

    /* retrieve the port number for listening */
    simplePort = atoi(argv[1]);

    /* setup the address structure */
    /* use INADDR_ANY to bind to all local addresses  */
    memset(&simpleServer, '\0', sizeof(simpleServer)); 
    simpleServer.sin_family = AF_INET;
    simpleServer.sin_addr.s_addr = htonl(INADDR_ANY);
    simpleServer.sin_port = htons(simplePort);

    /*  bind to the address and port with our socket  */
    returnStatus = bind(simpleSocket,(struct sockaddr *)&simpleServer,sizeof(simpleServer));

    if (returnStatus == 0) {
        fprintf(stderr, "Bind completed!\n");
    }
    else {
        fprintf(stderr, "Could not bind to address!\n");
        close(simpleSocket);
        exit(1);
    }

    /* lets listen on the socket for connections      */
    returnStatus = listen(simpleSocket, 5);

    if (returnStatus == -1) {
        fprintf(stderr, "Cannot listen on socket!\n");
        close(simpleSocket);
        exit(1);
    }

    while (1)
    {
        struct sockaddr_in clientName = { 0 };
        int simpleChildSocket = 0;
        int clientNameLength = sizeof(clientName);

        /* wait here */
        simpleChildSocket = accept(simpleSocket,(struct sockaddr *)&clientName, &clientNameLength);

        if (simpleChildSocket == -1) {
            fprintf(stderr, "Cannot accept connections!\n");
            close(simpleSocket);
            exit(1);
        }

        /* handle the new connection request  */
        /* write out our message to the client */
        write(simpleChildSocket, MESSAGE, strlen(MESSAGE));
        close(simpleChildSocket);
    }

    close(simpleSocket);
    return 0;
}

谢谢您的回答

标签: csocketstcpserverwrite

解决方案


一点介绍:关于原程序

该程序开始创建一个套接字并将其设置为侦听特定端口,并使用命令行(例如programName <port>.

端口号通过行检索simplePort = atoi(argv[1]);。可能会对参数进行更严格的检查(atoi()不检查是否实际提供了数字),但我认为这对于入门级教育计划是可以的。


之后,随着线

simpleChildSocket = accept(simpleSocket,(struct sockaddr *)&clientName, &clientNameLength);

accept()功能会一直阻塞,直到收到来自 TCP 客户端的连接请求。一旦 TCP 握手完成(SYN/ SYN-ACK/ ACK,它称为三次握手),就会返回一个套接字句柄(在您的情况下simpleChildSocket),它可用于与客户端交换数据。


欢迎留言

接受完成后,我们确信一切顺利,我们很快就会收到欢迎信息。随着线条

/* write out our message to the client */
write(simpleChildSocket, MESSAGE, strlen(MESSAGE));

字符串中包含的MESSAGE字符(用常量定义const char MESSAGE[] = "Hello student!\n";)通过write()函数发送。它的参数是

  • 套接字描述符
  • 指向要发送的缓冲区的指针
  • 要发送的字节数(在这种情况下,它对应于 的长度MESSAGE,计算公式为strlen(MESSAGE)

注意: write函数实际上可以使用,但它是一个非常规的选择。事实上,它是一个通用函数,但实际上是在写入套接字时send()使用的。


如何实现你的目标

您所要做的就是用包含日期的字符串替换MESSAGE调用write()

{
    char buff[30+1];
    time_t ticks = time(NULL);
    snprintf(buff, sizeof(buff), "%.30s\r\n", ctime(&ticks));

    /* write out our message to the client */
    write( simpleChildSocket, buff, strlen(buff) );
}

不要忘记定义你的buff字符缓冲区。我在本地定义它,但您也可以动态分配它。

您的老师提供的代码将时间计算复制到ctime()数组中buff(我增加了它的大小以确保整个日期时间可以包含在其中)。

然后我们write像以前一样调用,只是用新字符串and替换MESSAGEand 。strlen(MESSAGE)buffstrlen(buff)


推荐阅读