Linux系统ls命令的最简单实现及opendir和readdir函数回顾

Linux系统ls命令功能强大,可选项参数众多。我们这篇博文只是复习opendir和readdir函数,故提供ls命令的最简单实现,只显示文件和目录名称而已。

一、 数据结构
1. DIR – 目录流

DIR —— A type representing a directory stream. 
The DIR type may be an incomplete type.

2. structure dirent
In the glibc implementation, the dirent structure is defined as follows:

struct dirent {
    ino_t          d_ino;       /* Inode number */
    off_t          d_off;       /* Not an offset; see below */
    unsigned short d_reclen;    /* Length of this record */
    unsigned char  d_type;      /* Type of file; not supported by all filesystem types */
    char           d_name[256]; /* Null-terminated filename */
};

二、 函数介绍(opendir, readdir和closedir)
1. opendir函数 – 返回目录流

#include <sys/types.h>
#include <dirent.h>

DIR *opendir(const char *name);

// The  opendir() function opens a directory stream corresponding to the directory name, and returns a pointer to the directory
// stream.  The stream is positioned at the first entry in the directory.

2. readdir函数

#include <dirent.h>

struct dirent *readdir(DIR *dirp);

// The readdir() function returns a pointer to a dirent structure representing the next directory entry in the directory stream
// pointed to by dirp.  It returns NULL on reaching the end of the directory stream or if an error occurred.

3. closedir函数 – 关闭目录流

#include <sys/types.h>
#include <dirent.h>

int closedir(DIR *dirp);

// The  closedir()  function closes the directory stream associated with dirp.  A successful call to closedir() also closes the
// underlying file descriptor associated with dirp.  The directory stream descriptor dirp is not available after this call.

三、 编程实现
1. 源代码

#include <stdio.h>
#include <dirent.h>

int main(int argc, char *argv[])
{
    DIR *dirp;
    struct dirent *direntp;

    if (argc != 2) {
        printf("USAGE: %s directoryname\n", argv[0]);
        return 1;
    }

    if ((dirp = opendir(argv[1])) == NULL) {
        printf("cannot open %s\n", argv[1]);
        return 1;
    }

    while ((direntp = readdir(dirp)) != NULL) {
        printf("%s\t", direntp->d_name);
    }

    printf("\n");
    closedir(dirp);

    return 0;
}

2. 运行结果

[root@fedora Workspace]# ./myls /
media   tmp     sys     root    ..      srv     run     var     sbin    usr    etc      .       lib     opt     lib64   bin     home    dev     lost+found     mnt      boot    proc
[root@fedora Workspace]# ./myls ~
.tcshrc anaconda-ks.cfg Pictures        Music   .pki    ..      .mozilla       .bash_logout     .bashrc .config .viminfo        .bash_history   .cache  Videos .local   .bash_profile   .esd_auth       .       Templates       Downloads      .Xauthority      Desktop .cshrc  Public  .ICEauthority   .dbus   Documents

Leave a Reply

Your email address will not be published. Required fields are marked *