Конфликт с буфером realpath()

Вот моя функция, которая ищет обычные файлы в заданном каталоге, а затем сохраняет полный путь к ним в списке.

static my_func(const char *path, Files **list) //list - storage for file names
{
    DIR *d;
    struct dirent *dir;
    char buf[PATH_MAX + 1];

    d = opendir(path);
    if (d) {
        while ((dir = readdir(d)) != NULL) {
            if ((DT_REG == dir->d_type)) {

                realpath(dir->d_name, buf);
                List_push(list, buf);
                printf("%s\n", dir->d_name);
                // memset(buf, 0, PATH_MAX + 1);
            }
        }
    }
    closedir(d);
    return 0;
}
...
...

int main()
{
    // list creation
    // my_func call
    ...
    List_print(...)
}

Ожидаемый результат:

FILE_1.txt
FILE_2.txt
FILE_3.txt
FILE_4.txt
FILE_5.txt
/home/user/c/FILE_1.txt
/home/user/c/FILE_2.txt
/home/user/c/FILE_3.txt
/home/user/c/FILE_4.txt
/home/user/c/FILE_5.txt

Токовый выход:

FILE_1.txt
FILE_2.txt
FILE_3.txt
FILE_4.txt
FILE_5.txt
/home/user/c/FILE_1.txt
/home/user/c/FILE_1.txt
/home/user/c/FILE_1.txt
/home/user/c/FILE_1.txt
/home/user/c/FILE_1.txt

Может ли это быть связано с моей реализацией связанного списка? Это работает нормально, потому что я проверил это с:

List_push(list, dir->d_name)

и получил ожидаемые результаты. Это реализация List_push (файлы просто структура с char * и указатель на следующий элемент):

void List_push(Files **head, char *x)
{
    Files *new;

    new   = malloc(sizeof(Files));

    if (NULL != new) {
        new->next = *head;
        new->text = x;
        *head = new;
    } else {
        printf("malloc error");
    }

}

Кроме того, как вы можете видеть, я пытался очистить buf с memset, но безуспешно - вывод:

FILE_1.txt
FILE_2.txt
FILE_3.txt
FILE_4.txt
FILE_5.txt






[console]$

Да, пустое пространство, похоже, заполнено чем-то (или это просто '\n' символы из List_print), поэтому список не пуст.

Что здесь не так?

1 ответ

Решение

В List_push(list, buf); вы храните указатель на buf в списке. Вы делаете это для каждого файла, так что вы получите несколько указателей на один и тот же файл. buf в списке. При печати элементов списка он будет отображать (текущее) содержимое buf,

Чтобы избежать этого, вам нужно создать копию buf и сохранить это, чтобы сохраненные данные не были перезаписаны при повторном использовании buf для следующего файла.

Другие вопросы по тегам