/*
- Copyright (C) 2010-2014 wpitchoune@gmail.com
-
- This program 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 2 of the License, or
- (at your option) any later version.
-
- This program 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 this program; if not, write to the Free Software
- Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
- 02110-1301 USA
-*/
+ * Copyright (C) 2010-2015 jeanfi@gmail.com
+ *
+ * This program 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 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ * 02110-1301 USA
+ */
+#define _LARGEFILE_SOURCE 1
+#include "config.h"
#include <dirent.h>
+#include <fts.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/types.h>
+#include <plog.h>
#include <pio.h>
-
/* Directory separator is \ when cross-compiling for MS Windows
systems */
#if defined(__MINGW32__)
return npath;
}
-char **dir_list(const char *dpath, int (*filter) (const char *path))
+static char **paths_add(char **paths, int n, char *path)
+{
+ char **result;
+
+ result = malloc((n+1) * sizeof(void *));
+
+ memcpy(result + 1, paths, n * sizeof(void *));
+
+ *result = path;
+
+ return result;
+}
+
+char **dir_list(const char *dpath, int (*filter) (const char *))
{
struct dirent *ent;
DIR *dir;
- char **paths;
+ char **paths, *path, *name, **tmp;
int n;
dir = opendir(dpath);
*paths = NULL;
while ((ent = readdir(dir)) != NULL) {
- char *fpath;
- char *name = ent->d_name;
+ name = ent->d_name;
if (!strcmp(name, ".") || !strcmp(name, ".."))
continue;
- fpath = malloc(strlen(dpath) + 1 + strlen(name) + 1);
-
- strcpy(fpath, dpath);
- strcat(fpath, "/");
- strcat(fpath, name);
-
- if (!filter || filter(fpath)) {
- char **npaths;
+ path = path_append(dpath, name);
- n++;
- npaths = malloc(n * sizeof(void *));
- memcpy(npaths + 1, paths, (n - 1) * sizeof(void *));
+ if (!filter || filter(path)) {
+ tmp = paths_add(paths, n, path);
free(paths);
- paths = npaths;
- *npaths = fpath;
+ paths = tmp;
+ n++;
} else {
- free(fpath);
+ free(path);
}
}
page = malloc(size + 1);
if (!page || size != fread(page, 1, size, fp)) {
free(page);
- return NULL;
+ page = NULL;
+ } else {
+ *(page + size) = '\0';
}
- *(page + size) = '\0';
-
fclose(fp);
} else {
page = NULL;
long file_get_size(const char *path)
{
FILE *fp;
+ long size;
if (!is_file(path))
return -1;
fp = fopen(path, "rb");
if (fp) {
- long size;
-
if (fseek(fp, 0, SEEK_END) == -1)
- return -1;
-
- size = ftell(fp);
+ size = -1;
+ else
+ size = ftell(fp);
fclose(fp);
-
- return size;
+ } else {
+ size = -1;
}
- return -1;
+ return size;
}
#define FCOPY_BUF_SZ 4096
FILE *fsrc, *fdst;
int ret = 0;
+ log_fct("copy %s to %s", src, dst);
+
fsrc = fopen(src, "r");
if (fsrc) {
void mkdirs(const char *dirs, mode_t mode)
{
- char *c = (char *)dirs;
- char *dir = malloc(strlen(dirs) + 1);
+ char *c, *dir;
+ int i;
+
+ log_fct("mkdirs %s", dirs);
+
+ c = (char *)dirs;
+ dir = malloc(strlen(dirs) + 1);
- int i = 0;
+ i = 0;
while (*c) {
if ((*c == DIRSEP || *c == '\0') && c != dirs) {
strncpy(dir, dirs, i);
printf("File copy error: unknown error %d.\n", code);
}
}
+
+int dir_rcopy(const char *src, const char *dst)
+{
+ int ret;
+ char **paths;
+ FTS *ftsp;
+ FTSENT *p, *chp;
+ int fts_options = FTS_COMFOLLOW | FTS_LOGICAL | FTS_NOCHDIR;
+ char *p_dst, *n_dst;
+
+ log_fct_enter();
+
+ log_fct("copy dir %s to %s", src, dst);
+
+ paths = malloc(2 * sizeof(char *));
+ paths[0] = strdup(src);
+ paths[1] = NULL;
+
+ ftsp = fts_open(paths, fts_options, NULL);
+ if (!ftsp)
+ return 1;
+
+ chp = fts_children(ftsp, 0);
+ if (!chp)
+ return 0;
+
+ n_dst = dir_normalize(dst);
+
+ while ((p = fts_read(ftsp)) != NULL) {
+ switch (p->fts_info) {
+ case FTS_D:
+ p_dst = path_append(n_dst,
+ p->fts_path + strlen(src) + 1);
+ mkdirs(p_dst, 0777);
+ free(p_dst);
+ break;
+ case FTS_F:
+ p_dst = path_append(n_dst,
+ p->fts_path + strlen(src) + 1);
+ file_copy(p->fts_path, p_dst);
+ free(p_dst);
+ break;
+ default:
+ break;
+ }
+ }
+ fts_close(ftsp);
+
+ free(n_dst);
+ free(paths);
+
+ ret = 0;
+
+ log_fct_exit();
+
+ return ret;
+}