Files
android_bootable_recovery/libtar/wrapper.c
Ethan Yonker 1b7a31bd65 Track backup and restore progress
Track backup and restore progress based on the sizes of the files
as they are being added to the tar backup file. Update the
progress bar based on the sizes of the files.

Change-Id: Idf649efa1db3e91830b4b2add86203a3f30042ff
2014-07-09 08:52:18 -05:00

214 lines
4.6 KiB
C

/*
** Copyright 1998-2003 University of Illinois Board of Trustees
** Copyright 1998-2003 Mark D. Roth
** All rights reserved.
**
** wrapper.c - libtar high-level wrapper code
**
** Mark D. Roth <roth@uiuc.edu>
** Campus Information Technologies and Educational Services
** University of Illinois at Urbana-Champaign
*/
#define DEBUG
#include <internal.h>
#include <stdio.h>
#include <sys/param.h>
#include <dirent.h>
#include <errno.h>
#include <stdlib.h>
#ifdef STDC_HEADERS
# include <string.h>
#endif
int
tar_extract_glob(TAR *t, char *globname, char *prefix)
{
char *filename;
char buf[MAXPATHLEN];
int i, fd = 0;
while ((i = th_read(t)) == 0)
{
filename = th_get_pathname(t);
if (fnmatch(globname, filename, FNM_PATHNAME | FNM_PERIOD))
{
if (TH_ISREG(t) && tar_skip_regfile(t))
return -1;
continue;
}
if (t->options & TAR_VERBOSE)
th_print_long_ls(t);
if (prefix != NULL)
snprintf(buf, sizeof(buf), "%s/%s", prefix, filename);
else
strlcpy(buf, filename, sizeof(buf));
if (tar_extract_file(t, filename, prefix, &fd) != 0)
return -1;
}
return (i == 1 ? 0 : -1);
}
int
tar_extract_all(TAR *t, char *prefix, const int *progress_fd)
{
char *filename;
char buf[MAXPATHLEN];
int i;
printf("prefix: %s\n", prefix);
#ifdef DEBUG
printf("==> tar_extract_all(TAR *t, \"%s\")\n",
(prefix ? prefix : "(null)"));
#endif
while ((i = th_read(t)) == 0)
{
#ifdef DEBUG
puts(" tar_extract_all(): calling th_get_pathname()");
#endif
filename = th_get_pathname(t);
if (t->options & TAR_VERBOSE)
th_print_long_ls(t);
if (prefix != NULL)
snprintf(buf, sizeof(buf), "%s/%s", prefix, filename);
else
strlcpy(buf, filename, sizeof(buf));
#ifdef DEBUG
printf(" tar_extract_all(): calling tar_extract_file(t, "
"\"%s\")\n", buf);
#endif
printf("item name: '%s'\n", filename);
if (tar_extract_file(t, buf, prefix, progress_fd) != 0)
return -1;
}
return (i == 1 ? 0 : -1);
}
int
tar_append_tree(TAR *t, char *realdir, char *savedir, char *exclude)
{
#ifdef DEBUG
printf("==> tar_append_tree(0x%lx, \"%s\", \"%s\")\n",
(long unsigned int)t, realdir, (savedir ? savedir : "[NULL]"));
#endif
char temp[1024];
int skip = 0, i, n_spaces = 0;
char ** excluded = NULL;
char * p = NULL;
if (exclude) {
strcpy(temp, exclude);
p = strtok(exclude, " ");
if (p == NULL) {
excluded = realloc(excluded, sizeof(char*) * (++n_spaces));
excluded[0] = temp;
} else {
while (p) {
excluded = realloc(excluded, sizeof(char*) * (++n_spaces));
excluded[n_spaces-1] = p;
p = strtok(NULL, " ");
}
}
excluded = realloc(excluded, sizeof(char*) * (n_spaces+1));
excluded[n_spaces] = 0;
for (i = 0; i < (n_spaces+1); i++) {
if (realdir == excluded[i]) {
printf(" excluding '%s'\n", excluded[i]);
skip = 1;
break;
}
}
}
if (skip == 0) {
if (tar_append_file(t, realdir, savedir) != 0)
return -1;
}
char realpath[MAXPATHLEN];
char savepath[MAXPATHLEN];
struct dirent *dent;
DIR *dp;
struct stat s;
dp = opendir(realdir);
if (dp == NULL) {
if (errno == ENOTDIR)
return 0;
return -1;
}
while ((dent = readdir(dp)) != NULL) {
if(strcmp(dent->d_name, ".") == 0
|| strcmp(dent->d_name, "..") == 0)
continue;
if (exclude) {
int omit = 0;
for (i = 0; i < (n_spaces+1); i++) {
if (excluded[i] != NULL) {
if (strcmp(dent->d_name, excluded[i]) == 0 || strcmp(excluded[i], realdir) == 0) {
printf(" excluding '%s'\n", excluded[i]);
omit = 1;
break;
}
}
}
if (omit)
continue;
}
snprintf(realpath, MAXPATHLEN, "%s/%s", realdir, dent->d_name);
if (savedir)
snprintf(savepath, MAXPATHLEN, "%s/%s", savedir, dent->d_name);
if (lstat(realpath, &s) != 0)
return -1;
if (S_ISDIR(s.st_mode)) {
if (tar_append_tree(t, realpath, (savedir ? savepath : NULL), (exclude ? exclude : NULL)) != 0)
return -1;
continue;
} else {
if (tar_append_file(t, realpath, (savedir ? savepath : NULL)) != 0)
return -1;
continue;
}
}
closedir(dp);
free(excluded);
return 0;
}
int
tar_find(TAR *t, char *searchstr)
{
if (!searchstr)
return 0;
char *filename;
int i, entryfound = 0;
#ifdef DEBUG
printf("==> tar_find(0x%lx, %s)\n", (long unsigned int)t, searchstr);
#endif
while ((i = th_read(t)) == 0) {
filename = th_get_pathname(t);
if (fnmatch(searchstr, filename, FNM_FILE_NAME | FNM_PERIOD) == 0) {
entryfound++;
#ifdef DEBUG
printf("Found matching entry: %s\n", filename);
#endif
break;
}
}
#ifdef DEBUG
if (!entryfound)
printf("No matching entry found.\n");
#endif
return entryfound;
}