+++ /dev/null
-/*
- This file is part of GNUnet.
- Copyright (C) 2001--2013 GNUnet e.V.
-
- GNUnet is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published
- by the Free Software Foundation; either version 3, or (at your
- option) any later version.
-
- GNUnet is distributed in the hope that it will be useful, but
- WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with GNUnet; see the file COPYING. If not, write to the
- Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- Boston, MA 02110-1301, USA.
-*/
-/**
- * @file util/disk_iterator.c
- * @brief asynchronous iteration over a directory
- * @author Christian Grothoff
- * @author Nils Durner
- */
-#include "platform.h"
-#include "gnunet_util_lib.h"
-#include "disk.h"
-
-#define LOG(kind,...) GNUNET_log_from (kind, "util", __VA_ARGS__)
-
-#define LOG_STRERROR(kind,syscall) GNUNET_log_from_strerror (kind, "util", syscall)
-
-#define LOG_STRERROR_FILE(kind,syscall,filename) GNUNET_log_from_strerror_file (kind, "util", syscall, filename)
-
-
-/**
- * Opaque handle used for iterating over a directory.
- */
-struct GNUNET_DISK_DirectoryIterator
-{
-
- /**
- * Function to call on directory entries.
- */
- GNUNET_DISK_DirectoryIteratorCallback callback;
-
- /**
- * Closure for @e callback.
- */
- void *callback_cls;
-
- /**
- * Reference to directory.
- */
- DIR *directory;
-
- /**
- * Directory name.
- */
- char *dirname;
-
- /**
- * Next filename to process.
- */
- char *next_name;
-
- /**
- * Our priority.
- */
- enum GNUNET_SCHEDULER_Priority priority;
-
-};
-
-
-/**
- * Task used by the directory iterator.
- */
-static void
-directory_iterator_task (void *cls)
-{
- struct GNUNET_DISK_DirectoryIterator *iter = cls;
- char *name;
-
- name = iter->next_name;
- GNUNET_assert (name != NULL);
- iter->next_name = NULL;
- iter->callback (iter->callback_cls, iter, name, iter->dirname);
- GNUNET_free (name);
-}
-
-
-/**
- * This function must be called during the DiskIteratorCallback
- * (exactly once) to schedule the task to process the next
- * filename in the directory (if there is one).
- *
- * @param iter opaque handle for the iterator
- * @param can set to #GNUNET_YES to terminate the iteration early
- * @return #GNUNET_YES if iteration will continue,
- * #GNUNET_NO if this was the last entry (and iteration is complete),
- * #GNUNET_SYSERR if abort was YES
- */
-int
-GNUNET_DISK_directory_iterator_next (struct GNUNET_DISK_DirectoryIterator *iter,
- int can)
-{
- struct dirent *finfo;
-
- GNUNET_assert (iter->next_name == NULL);
- if (can == GNUNET_YES)
- {
- CLOSEDIR (iter->directory);
- GNUNET_free (iter->dirname);
- GNUNET_free (iter);
- return GNUNET_SYSERR;
- }
- while (NULL != (finfo = READDIR (iter->directory)))
- {
- if ((0 == strcmp (finfo->d_name, ".")) ||
- (0 == strcmp (finfo->d_name, "..")))
- continue;
- GNUNET_asprintf (&iter->next_name, "%s%s%s", iter->dirname,
- DIR_SEPARATOR_STR, finfo->d_name);
- break;
- }
- if (finfo == NULL)
- {
- GNUNET_DISK_directory_iterator_next (iter, GNUNET_YES);
- return GNUNET_NO;
- }
- GNUNET_SCHEDULER_add_with_priority (iter->priority, &directory_iterator_task,
- iter);
- return GNUNET_YES;
-}
-
-
-/**
- * Scan a directory for files using the scheduler to run a task for
- * each entry. The name of the directory must be expanded first (!).
- * If a scheduler does not need to be used, GNUNET_DISK_directory_scan
- * may provide a simpler API.
- *
- * @param prio priority to use
- * @param dir_name the name of the directory
- * @param callback the method to call for each file
- * @param callback_cls closure for @a callback
- * @return #GNUNET_YES if directory is not empty and @a callback
- * will be called later, #GNUNET_NO otherwise, #GNUNET_SYSERR on error.
- */
-int
-GNUNET_DISK_directory_iterator_start (enum GNUNET_SCHEDULER_Priority prio,
- const char *dir_name,
- GNUNET_DISK_DirectoryIteratorCallback
- callback, void *callback_cls)
-{
- struct GNUNET_DISK_DirectoryIterator *di;
-
- di = GNUNET_new (struct GNUNET_DISK_DirectoryIterator);
- di->callback = callback;
- di->callback_cls = callback_cls;
- di->directory = OPENDIR (dir_name);
- if (di->directory == NULL)
- {
- GNUNET_free (di);
- callback (callback_cls, NULL, NULL, NULL);
- return GNUNET_SYSERR;
- }
- di->dirname = GNUNET_strdup (dir_name);
- di->priority = prio;
- return GNUNET_DISK_directory_iterator_next (di, GNUNET_NO);
-}
-
-/* end of disk_iterator */