【问题标题】:C socket, send message after file, TCPC套接字,文件后发送消息,TCP
【发布时间】:2015-02-07 20:41:33
【问题描述】:

我想通过套接字发送文件,然后我想发送三个消息。下面的代码有效,但我必须两次发送第一句话。我的问题是为什么?没有一个句子 1,接收者显示句子 2、句子 3 和句子 3。这段代码有什么问题? 我正在使用 tcp 协议。

发件人.c

char file_size[256];
struct stat file_stat;
int sent_bytes = 0;
int fd;
int offset;
int remain_data;

fd = open(FILE_TO_SEND, O_RDONLY);
if (fd == -1)
{
        fprintf(stderr, "Error opening file --> %s", strerror(errno));

        exit(EXIT_FAILURE);
}

/* Get file stats */
if (fstat(fd, &file_stat) < 0)
{
        fprintf(stderr, "Error fstat --> %s", strerror(errno));

        exit(EXIT_FAILURE);
}

fprintf(stdout, "File Size: \n%d bytes\n", file_stat.st_size);

sprintf(file_size, "%d", file_stat.st_size);

write(sck, file_size, 256);

char buffer[1024] = "";


while (1) {
    int bytes_read = read(fd, buffer, sizeof(buffer));
    if (bytes_read == 0) 
        break;

    void *p = buffer;
    while (bytes_read > 0) {
        int bytes_written = write(sck, p, bytes_read);
        if (bytes_written <= 0) {
            // handle errors
        }
        bytes_read -= bytes_written;
        p += bytes_written;

    }
}


char sentence[1024];


write(sck, sentence1, 1024);

write(sck, sentence1, 1024);

write(sck, sentence2, 1024);

write(sck, sentence3, 1024);

接收者.c

char buffer[1024] = "";
int sck = *((int*) arg);

int file_size;

read(sck, buffer, 256);
file_size = atoi(buffer);

ssize_t len;
FILE *received_file;
int remain_data = 0;


received_file = fopen("plik.pdf", "w");
if (received_file == NULL)
{
        fprintf(stderr, "Failed to open file foo --> %s\n", strerror(errno));

        exit(EXIT_FAILURE);
}

remain_data = file_size;

while (((len = recv(sck, buffer, 1024, 0)) > 0) && (remain_data > 0))
{
        fwrite(buffer, sizeof(char), len, received_file);
        remain_data -= len;
}
fclose(received_file);



read (sck, buffer, 1024);
printf("%s 1\n", buffer);    

read (sck, buffer, 1024);
printf("%s 2\n", buffer);

read (sck, buffer, 1024);
printf("%s 3\n", buffer);

【问题讨论】:

  • 查看生成的文件,第一句是不是写在文件末尾?
  • write(2)send(2) 保证数据已完全发送。如果调用被信号处理程序或其他东西中断怎么办?在生产代码中,始终检查这些系统调用的返回值。

标签: c linux sockets send


【解决方案1】:

与 TCP 协议无关。你的逻辑有问题。您正在接收数据,然后检查剩余数据。所以你的 sentence1 在 while 循环中被接收和丢弃。

将你的 recv() 移动到 while 的主体中以解决此问题或更改 while 中的顺序。

while ((remain_data > 0) && ((len = recv(sck, buffer, 1024, 0)) > 0))

在修改后的 while 中,只有当剩余数据 > 0 时才调用 recv()。如果剩余数据 == 0(惰性求值),则不会调用 recv()。因此,您的 while 循环在收到文件并准备好接收您的句子后立即结束。在您的代码中,while 循环读取第一句话,然后检查剩余数据 > 0 有效地丢弃了 sentence1

【讨论】:

    猜你喜欢
    • 2019-03-31
    • 2014-11-20
    • 1970-01-01
    • 2013-07-28
    • 1970-01-01
    • 1970-01-01
    • 2015-01-09
    • 2012-03-25
    • 1970-01-01
    相关资源
    最近更新 更多