0
  • コンパイラ:Code :: Blocks(GNU GCC)
  • プラットフォーム:Windows(x86)

更新:opendir()を呼び出す前に、chdir()を使用して現在の作業ディレクトリを変更することで、問題を解決しました。したがって、opendir()は、現在の作業ディレクトリにあるディレクトリのみを開くことができると想定しています。だから私の新しい質問は、私は正しいですか?

私は現在、windowのdirコマンドの基本的な模倣を書いています。「。」の場合、私のプログラムは正しく動作します。opendir()の引数としてワイルドカードが使用されます。しかし、ワイルドカードを使用せず、代わりにディレクトリを指定する場合。私のプログラムは、指定されたディレクトリを開きません。たとえば、c:\ windowsと入力すると、代わりにc:\が開き、各ファイルのst_modeは同じになります。少なくとも、すべてのファイルタイプ(DIR、FILE、OTHER)が同じであるため、これらはすべて同じであると思います。

#include <stdio.h>
#include <string.h>

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

int main(int argc, char* argv[])
{
//'directory' points to the directory | 'directory_contents' is used with readdir() to read the directory's('directory') contents.
DIR *directory;
struct dirent *directory_contents;
struct stat file_info;

//IF no argument is present display the contents of the current directory | IF there is an arugment display the contents of that argument | ELSE Too many arguments
if (argc == 1)
{
    directory = opendir(".");
}
else if (argc == 2)
{
    //New Code
    chdir(argv[1]); directory = opendir(".");

    //Old Code
    directory = opendir(argv[1]);
}
else
{
    printf("ERROR: Extra arguments\n");
}

//Checks to see if the directory opened above was actually opened.
if (directory == NULL)
{
    printf("ERROR: Failed to open '%s'.\n", argv[1]);
    return 2;
}
else
{
    //WHILE there are file names to be read THEN read the file names
    while (directory_contents = readdir(directory))
    {
        stat(directory_contents->d_name, &file_info);

        //Test for directory
        if(S_ISDIR(file_info.st_mode))
        {
            //File type
            printf("<DIR>   ");

            //File name
            if(strlen(directory_contents->d_name) <= 15)
            {
                printf("%-15s", directory_contents->d_name);
            }
            else if(strlen(directory_contents->d_name) > 15)
            {
                printf("%.12s.. ", directory_contents->d_name);
            }

            //File premissions
            printf("<%c%c%c>\n", ((file_info.st_mode & S_IRUSR)==0) ? '-' : 'r', ((file_info.st_mode & S_IWUSR)==0) ? '-' : 'w', ((file_info.st_mode & S_IXUSR)==0) ? '-' : 'x');
        }
        //Test for a regular file.
        else if(S_ISREG(file_info.st_mode))
        {
            //File type
            printf("<FILE>  ");

            //File name
            if(strlen(directory_contents->d_name) <= 15)
            {
                printf("%-15s", directory_contents->d_name);
            }
            else if(strlen(directory_contents->d_name) > 15)
            {
                printf("%.12s.. ", directory_contents->d_name);
            }

            //File premissions
            printf("<%c%c%c> ", ((file_info.st_mode & S_IRUSR)==0) ? '-' : 'r', ((file_info.st_mode & S_IWUSR)==0) ? '-' : 'w', ((file_info.st_mode & S_IXUSR)==0) ? '-' : 'x');

            //File size
            if (file_info.st_size < 1000)
            {
                printf("<%-3i B>\n", file_info.st_size);
            }
            else if ( (file_info.st_size > 1000) && (file_info.st_size < 1000000) )
            {
                printf("<%-3i KB>\n", file_info.st_size/1000);
            }
            else if ( (file_info.st_size > 1000000) && (file_info.st_size < 1000000000) )
            {
                printf("<%-3i MB>\n", file_info.st_size/1000000);
            }
            else
            {
                printf("<%-3i GB>\n", file_info.st_size/1000000000);
            }
        }
        //Symbolic Link etc.
        else
        {
            //File type
            printf("<OTHER> ");

            //File name
            if(strlen(directory_contents->d_name) <= 15)
            {
                printf("%-15s", directory_contents->d_name);
            }
            else if(strlen(directory_contents->d_name) > 15)
            {
                printf("%.12s.. ", directory_contents->d_name);
            }

            //File premissions
            printf("<%c%c%c>\n", ((file_info.st_mode & S_IRUSR)==0) ? '-' : 'r', ((file_info.st_mode & S_IWUSR)==0) ? '-' : 'w', ((file_info.st_mode & S_IXUSR)==0) ? '-' : 'x');
        }
    }
}
}

そして、はい、私が出力しているパーミッションは、WindowがACLを使用しているため、完全に無関係であることを私は知っています。私は今のところ選択の余地がないので、このプログラムをWindowsでのみ書いていますが、LinuxOSを対象としています。

4

1 に答える 1

1

stat(directory_contents->d_name,

この行が問題です。このd_nameフィールドは、ディレクトリを含まないファイルの名前です。したがって、ディレクトリがたまたま現在のディレクトリでない限り、toを呼び出してstat()もファイルは見つかりません。

于 2013-01-17T17:45:56.700 に答える