zoukankan      html  css  js  c++  java
  • Linux通过AIO进行异步读文件

    下面列出源代码:

    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    
    #include <aio.h>
    #include <unistd.h>
    #include <signal.h>
    #include <sys/stat.h>
    #include <fcntl.h>
    
    
    static char *memBuffer;
    static int sFileDesc;
    static struct sigaction sOldSigAction;
    
    static void MySigQuitHandler(int sig)
    {
        printf("Signal Quit! The number is: %d
    ", sig);
    }
    
    static void MyFileReadCompleteProcedure(int sig, siginfo_t *si, void *ucontext)
    {
        printf("The file length is: %zu, and the content is: %s
    ", strlen(memBuffer), memBuffer);
        int status = close(sFileDesc);
        if(status == 0)
            puts("File closed successfully!");
        else
            printf("The error code is: %d
    ", status);
    
        free(memBuffer);
    
        // 还原原来的SIGUSR1信号行为
        if(sigaction(SIGUSR1, &sOldSigAction, NULL) == -1)
            puts("SIGUSR1 signal restore failed!");
    }
    
    int main(void)
    {
        struct sigaction sigAction = { .sa_flags = SA_RESTART, .sa_handler = &MySigQuitHandler };
    
        sigemptyset(&sigAction.sa_mask);
    
        if (sigaction(SIGQUIT, &sigAction, NULL) == -1)
        {
            puts("Signal failed!");
            return -1;
        }
    
        sigAction.sa_sigaction = &MyFileReadCompleteProcedure;
        if(sigaction(SIGUSR1, &sigAction, &sOldSigAction) == -1)
        {
            puts("Signal failed!");
            return -1;
        }
    
        const char *filePath = "myfile.txt";
    
        const mode_t mode = S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH;
        sFileDesc = open(filePath, O_RDONLY, mode);
        if(sFileDesc == -1)
        {
            printf("The file: %s cannot be opened!
    ", filePath);
            return -1;
        }
    
        const long fileLength = lseek(sFileDesc, 0, SEEK_END);
        lseek(sFileDesc, 0, SEEK_SET);
    
        memBuffer = malloc(fileLength + 1);
        memBuffer[fileLength] = '';
    
        struct aiocb aioBuffer;
        aioBuffer.aio_fildes = sFileDesc;
        aioBuffer.aio_offset = 0;
        aioBuffer.aio_buf = memBuffer;
        aioBuffer.aio_nbytes = fileLength;
        aioBuffer.aio_reqprio = 0;
        aioBuffer.aio_sigevent = (struct sigevent){.sigev_notify = SIGEV_SIGNAL, .sigev_signo = SIGUSR1, .sigev_value.sival_ptr = memBuffer };
    
        aio_read(&aioBuffer);
    
        getchar();
    
        return 0;
    }

    其中,上述代码实现中采用SIGUSR1信号进行捕获文件读完成事件,当然,这里也可以用SIGIO信号。

    另外,在编译链接时必须添加-lrt命令选项,因为rt库才包含了系统底层的API。

  • 相关阅读:
    demo12-回到顶部
    demo11-友情链接
    demo10-超链接标签
    demo09-程序员练习
    demo08-图片标签
    demo07-盒子标签
    demo06-字体标签
    demo05-换行标签
    转&nbsp;j2ee&nbsp;.线程池.对象池,连接池
    几种开源Java&nbsp;Web容器线程池…
  • 原文地址:https://www.cnblogs.com/zenny-chen/p/4153404.html
Copyright © 2011-2022 走看看