C言語入門(33) 実際にプログラムを読んで理解を深めよう ls編(7)

Posted: 2013年03月28日

前回は、colortype関数を解説してきました。
今回はprintaname関数が表示処理に用いているprintlong関数を解説していきます。

print.c printlong関数です。

プログラムプログラム:

void
printlong(const DISPLAY *dp)
{
    struct stat *sp;
    FTSENT *p;
    NAMES *np;
    char buf[20];
#ifdef COLORLS
    int color_printed = 0;
#endif

    if ((dp->list == NULL || dp->list->fts_level != FTS_ROOTLEVEL) &&
        (f_longform || f_size)) {
        (void)printf("total %lun", howmany(dp->btotal, blocksize));
    }

    for (p = dp->list; p; p = p->fts_link) {
        if (IS_NOPRINT(p))
            continue;
        sp = p->fts_statp;
        if (f_inode)
            (void)printf("%*ju ",
                dp->s_inode, (uintmax_t)sp->st_ino);
        if (f_size)
            (void)printf("%*jd ",
                dp->s_block, howmany(sp->st_blocks, blocksize));
        strmode(sp->st_mode, buf);
        aclmode(buf, p);
        np = p->fts_pointer;
        (void)printf("%s %*u %-*s  %-*s  ", buf, dp->s_nlink,
            sp->st_nlink, dp->s_user, np->user, dp->s_group,
            np->group);
        if (f_flags)
            (void)printf("%-*s ", dp->s_flags, np->flags);
        if (f_label)
            (void)printf("%-*s ", dp->s_label, np->label);
        if (S_ISCHR(sp->st_mode) || S_ISBLK(sp->st_mode))
            printdev(dp->s_size, sp->st_rdev);
        else
            printsize(dp->s_size, sp->st_size);
        if (f_accesstime)
            printtime(sp->st_atime);
        else if (f_birthtime)
            printtime(sp->st_birthtime);
        else if (f_statustime)
            printtime(sp->st_ctime);
        else
            printtime(sp->st_mtime);
#ifdef COLORLS
        if (f_color)
            color_printed = colortype(sp->st_mode);
#endif
        (void)printname(p->fts_name);
#ifdef COLORLS
        if (f_color && color_printed)
            endcolor(0);
#endif
        if (f_type)
            (void)printtype(sp->st_mode);
        if (S_ISLNK(sp->st_mode))
            printlink(p);
        (void)putchar('n');
    }
}

解説解説:

初回のコマンド引数で判断したフラグ通り表示します。
フラグをチェックして表示するかを処理します。

今回登場した表示関数(printdev等)は、次回解説します。
また、表示関数以外の関数(strmode)は次次回解説します。

度々登場しているhowmeny関数については以下の実装になっています。

#ifndef howmany
#define howmany(x,y)    (((x)+((y)-1))/(y))
#endif

howmany関数は、繰り上げ処理を行なっています。
今回の場合ブロック数(1024byte=1block)を計算する際
1025は2blockになるため繰り上げを行います。
引数には、整数型の変数を渡さないと微妙な計算になるため
使用には気をつける必要がありますが・・・

カテゴリー: プログラム, 入門 | タグ: , , | コメント無し »

コメント