You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

异步I/O:如何获取I/O请求中代码"认为"已写入的字节数?

POSIX异步IO获取实际写入字节数的方法

在使用aio.h的异步IO操作中,完全可以获取请求完成后实际写入的字节数,核心是用aio_return()函数,配合aio_error()做前置检查,具体操作如下:

  • 核心函数用法
    异步写请求提交后,必须等请求完成(不管成功还是失败),才能调用aio_return()获取结果。而且这个函数只能调用一次,调用后会清空相关状态。
    步骤:

    1. 用aio_error()检查请求状态:返回EINPROGRESS说明请求还在进行,需要等待;返回0说明请求成功;返回其他值说明请求失败。
    2. 请求成功时,aio_return()的返回值就是实际写入的字节数,正常情况下应该和你在struct aiocb中设置的aio_nbytes一致;请求失败时,aio_return()返回的是对应的错误码(和errno取值一致)。
  • 代码示例

    #include <aio.h>
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    #include <unistd.h>
    #include <errno.h>
    
    int main() {
        int fd = open("test.txt", O_WRONLY | O_CREAT | O_TRUNC, 0644);
        if (fd == -1) {
            perror("open failed");
            exit(EXIT_FAILURE);
        }
    
        char buf[] = "test async write";
        struct aiocb cb = {0};
        cb.aio_fildes = fd;
        cb.aio_buf = buf;
        cb.aio_nbytes = strlen(buf);
        // 若需要指定偏移量,设置cb.aio_offset
    
        // 提交异步写请求
        if (aio_write(&cb) == -1) {
            perror("aio_write submit failed");
            close(fd);
            exit(EXIT_FAILURE);
        }
    
        // 等待请求完成
        while (aio_error(&cb) == EINPROGRESS) {
            sched_yield(); // 让出CPU,避免忙等
        }
    
        // 获取结果
        int err = aio_error(&cb);
        if (err == 0) {
            ssize_t written = aio_return(&cb);
            printf("实际写入 %zd 字节(预期 %zd)\n", written, cb.aio_nbytes);
            if (written != cb.aio_nbytes) {
                fprintf(stderr, "警告:写入字节数与预期不符,可能是磁盘满或权限问题\n");
            }
        } else {
            fprintf(stderr, "异步写失败:%s\n", strerror(err));
        }
    
        // 同步并关闭文件
        if (aio_fsync(O_SYNC, &cb) == -1) {
            perror("aio_fsync failed");
        }
        close(fd);
        return 0;
    }
    
  • 针对你的场景的排查建议
    你遇到大量文件长度为0的情况,结合异步IO的特性,可能的原因包括:

    1. 异步请求提交失败:你可能没检查aio_write()的返回值,如果提交时就失败(比如文件打开错误、参数非法),自然不会有写入。
    2. 请求执行失败:比如磁盘空间不足、文件权限错误,此时aio_error()会返回对应错误码,比如ENOSPC、EACCES。
    3. 请求未完成就关闭文件:如果在异步写还没结束时就调用close(),会导致写入被中断,文件可能停留在0长度。
    4. aiocb结构体被提前释放/修改:多线程场景下,如果struct aiocb是栈上分配的,线程退出后结构体被销毁,异步IO的后续操作会出问题。

内容的提问来源于stack exchange,提问作者bob.sacamento

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.18 21:53:17