Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <errno.h> /* EINVAL */
- #include <signal.h> /* signal () */
- #include <sys/wait.h> /* wait () */
- #include <unistd.h> /* fork (), execvp (), _exit () */
- #include <assert.h>
- #include <math.h>
- #include <stdarg.h>
- #include <stdio.h> /* remove () */
- #include <string.h> /* memcmp */
- #include <stdlib.h> /* qsort */
- #include <limits.h> /* INT_MAX */
- #include <dirent.h>
- #include <event2/util.h>
- #include <inttypes.h> /* uintN_t */
- #include <time.h> /* time_t */
- #ifdef _MSC_VER
- typedef intptr_t ssize_t;
- #endif
- #define TR_PATH_DELIMITER '/'
- #define TR_PATH_DELIMITER_STR "/"
- #if !defined (__cplusplus)
- #ifdef HAVE_STDBOOL_H
- #include <stdbool.h>
- #elif !defined (__bool_true_false_are_defined)
- #define bool uint8_t
- #define true 1
- #define false 0
- #endif
- #endif
- typedef void * tr_sys_dir_t;
- typedef struct tr_ptrArray
- {
- void ** items;
- int n_items;
- int n_alloc;
- }
- tr_ptrArray;
- const tr_ptrArray TR_PTR_ARRAY_INIT = { NULL, 0, 0 };
- void*
- tr_malloc (size_t size)
- {
- return size ? malloc (size) : NULL;
- }
- #define tr_new(struct_type, n_structs) \
- ((struct_type *) tr_malloc (sizeof (struct_type) * ((size_t)(n_structs))))
- char*
- tr_buildPath (const char *first_element, ...)
- {
- const char * element;
- char * buf;
- char * pch;
- va_list vl;
- size_t bufLen = 0;
- /* pass 1: allocate enough space for the string */
- va_start (vl, first_element);
- element = first_element;
- while (element)
- {
- bufLen += strlen (element) + 1;
- element = va_arg (vl, const char*);
- }
- pch = buf = tr_new (char, bufLen);
- va_end (vl);
- if (buf == NULL)
- return NULL;
- /* pass 2: build the string piece by piece */
- va_start (vl, first_element);
- element = first_element;
- while (element)
- {
- const size_t elementLen = strlen (element);
- memcpy (pch, element, elementLen);
- pch += elementLen;
- *pch++ = TR_PATH_DELIMITER;
- element = va_arg (vl, const char*);
- }
- va_end (vl);
- /* terminate the string. if nonempty, eat the unwanted trailing slash */
- if (pch != buf)
- --pch;
- *pch++ = '\0';
- /* sanity checks & return */
- assert (pch - buf == (off_t)bufLen);
- return buf;
- }
- /** @brief Platform-specific invalid directory descriptor constant. */
- #define TR_BAD_SYS_DIR ((tr_sys_dir_t)NULL)
- tr_sys_dir_t
- tr_sys_dir_open (const char * path)
- {
- tr_sys_dir_t ret;
- assert (path != NULL);
- ret = opendir (path);
- return ret;
- }
- const char *
- tr_sys_dir_read_name (tr_sys_dir_t handle)
- {
- const char * ret = NULL;
- struct dirent * entry;
- assert (handle != TR_BAD_SYS_DIR);
- errno = 0;
- entry = readdir (handle);
- if (entry != NULL)
- ret = entry->d_name;
- return ret;
- }
- bool
- tr_sys_dir_close (tr_sys_dir_t handle)
- {
- bool ret;
- assert (handle != TR_BAD_SYS_DIR);
- ret = closedir (handle) != -1;
- return ret;
- }
- /**
- * This convoluted code does something (seemingly) simple:
- * remove the torrent's local files.
- *
- * Fun complications:
- * 1. Try to preserve the directory hierarchy in the recycle bin.
- * 2. If there are nontorrent files, don't delete them...
- * 3. ...unless the other files are "junk", such as .DS_Store
- */
- static void
- deleteLocalData (const char *tmpdir)
- {
- tr_sys_dir_t odir;
- /***
- **** Remove tmpdir.
- ****
- **** Try deleting the top-level files & folders to preserve
- **** the directory hierarchy in the recycle bin.
- **** If case that fails -- for example, rmdir () doesn't
- **** delete nonempty folders -- go from the bottom up too.
- ***/
- fprintf(stderr, "Started Delete on %s\n", tmpdir);
- /* try deleting the local data's top-level files & folders */
- if ((odir = tr_sys_dir_open (tmpdir)) != TR_BAD_SYS_DIR)
- {
- const char * name;
- int i = 0;
- while ((name = tr_sys_dir_read_name (odir)) != NULL && i <6)
- {
- if (strcmp (name, ".") != 0 && strcmp (name, "..") != 0)
- {
- i++;
- char * file = tr_buildPath (tmpdir, name, NULL);
- fprintf(stderr, "Try Delete on %s\n", file);
- //The call to remove(file) is causing tr_sys_dir_read_name (odir) to return the first item again instead of NULL when reaching the end of the directory listings
- remove (file);
- }
- }
- fprintf(stderr, "Closing with i = %i\n", i);
- tr_sys_dir_close (odir);
- }
- }
- int
- main (void)
- {
- deleteLocalData("/mnt/test/Downloads/Completed/gap/");
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement