如何包含linux_dirent64结构使用的s64和u64类型?

时间:2019-01-17 17:14:22

标签: c linux

我正在尝试在64位Ubuntu上使用getdents64 Linux syscall。我的代码是基于getdents man page的一个最小示例,如下所示:

    #define _GNU_SOURCE
#include <dirent.h>     /* Defines DT_* constants */
#include <fcntl.h>
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/stat.h>
#include <sys/syscall.h>
#include <sys/types.h>
#define handle_error(msg) do { perror(msg); exit(EXIT_FAILURE); } while (0)

struct linux_dirent64 {
    u64 d_ino;
    s64 d_off;
    unsigned short d_reclen;
    unsigned char d_type;
    char d_name[0];
};


#define BUF_SIZE 1024

int
main(int argc, char *argv[])
{
    int fd, nread;
    char buf[BUF_SIZE];
    struct linux_dirent64 *d;
    int bpos;
    char d_type;

    fd = open(argc > 1 ? argv[1] : ".", O_RDONLY | O_DIRECTORY);
    if (fd == -1)
        handle_error("open");

    for ( ; ; ) {
        nread = syscall(SYS_getdents64, fd, buf, BUF_SIZE);
        if (nread == -1)
            handle_error("getdents64");

        if (nread == 0)
            break;

        printf("--------------- nread=%d ---------------\n", nread);
        printf("inode#    file type  d_reclen  d_off   d_name\n");
        for (bpos = 0; bpos < nread;) {
            d = (struct linux_dirent64 *) (buf + bpos);
            printf("%8d  ", d->d_ino);
            d_type = *(buf + bpos + d->d_reclen - 1);
            printf("%-10s ", (d_type == DT_REG) ?  "regular" :
                             (d_type == DT_DIR) ?  "directory" :
                             (d_type == DT_FIFO) ? "FIFO" :
                             (d_type == DT_SOCK) ? "socket" :
                             (d_type == DT_LNK) ?  "symlink" :
                             (d_type == DT_BLK) ?  "block dev" :
                             (d_type == DT_CHR) ?  "char dev" : "???");
            printf("%4d %10lld  %s\n", d->d_reclen,
                    (long long) d->d_off, d->d_name);
            bpos += d->d_reclen;
        }
    }

    exit(EXIT_SUCCESS);
}

真正重要的部分(我的代码在其中中断)是

struct linux_dirent64 {
    u64 d_ino; // this is this problem
    s64 d_off; // this too
    unsigned short d_reclen;
    unsigned char d_type;
    char d_name[0];
};

当我编译程序时,出现以下错误:

hc-24@HP24:~$ gcc v.c 
v.c:14:5: error: unknown type name ‘u64’
     u64 d_ino;
     ^
v.c:15:5: error: unknown type name ‘s64’
     s64 d_off;
     ^

我认为问题是我包括sys/types.h,试图获得s64u64。我找到了某人在线使用linux_dirent64的示例,而他们只是#include <types.h>。当我尝试这样做时,出现错误:

hc-24@HP24:~$ gcc v.c 
love.c:8:19: fatal error: types.h: No such file or directory
compilation terminated.

因此,我必须以某种方式导入这两种类型(s64u64),我完全不知道。任何建议,我们将不胜感激。谢谢!

1 个答案:

答案 0 :(得分:0)

我想C4129: '#' : unrecognized character escape sequence C4129: ':' : unrecognized character escape sequence sprintf(szBuf,"1312:%d\#%s\:",iVal,pUser) 是Linux内核源代码中的头文件。

有关来源,请参见this链接。

以下是该文件的摘录:

<types.h>

所以,我想您可以将其添加到您的代码中以便对其进行编译。

#if defined(__GNUC__)
typedef u64         uint64_t;
typedef u64         u_int64_t;
typedef s64         int64_t;
#endif