int reverse, exitonerror;
int overwrite, accept, acceptdir, ignoredirmd;
int ops_total, ops_completed;
+ int ops_remove, ops_remove_completed;
+ int ops_update, ops_update_completed;
+ int ops_install, ops_install_completed;
int progress; /* type of progress meter */
};
printf("usage: zpm $scriptname [-fncC] args ...\n");
}
+static void pdots(int len, int ch, int was, int now, int total) {
+ was = len * was / total;
+ if (now > total) {
+ now = total;
+ }
+ now = len * now / total;
+ while (was++ < now) {
+ putchar(ch);
+ }
+ fflush(stdout);
+}
+
static int seterror(struct config *conf, char *msgfmt, ...) {
char msg[1024];
va_list ap;
return 0;
}
+ errno = 0;
+
if (lstat(dest, &st) == -1) {
- return seterror(conf,"can't stat");
+ switch (errno) {
+ case ENOENT:
+ /* TODO chatter if verbose */
+ break;
+ case ENOTEMPTY: /* fall through */
+ case EEXIST:
+ /* TODO chatter, or possibly require */
+ break;
+ default:
+ return seterror(conf, "can't stat %s: %s", dest, strerror(errno));
+ }
+ return 0;
}
if (S_ISDIR(st.st_mode)) {
/* TODO check that expected filetype matches actual filetype */
if (conf->verbose) {
- fprintf(stderr, "%s(%s)\n", flags ? "rmdir" : "unlink", dest);
+ if (conf->progress == 2) {
+ fprintf(stderr, "%s(%s)\n", flags ? "rmdir" : "unlink", dest);
+ } else if (conf->progress == 1) {
+ /* overwrite */
+ pdots(50, '.', conf->ops_completed, conf->ops_completed + 1, conf->ops_total);
+ conf->ops_completed++;
+ conf->ops_completed++;
+ } else {
+ pdots(50, '.', conf->ops_completed, conf->ops_completed + 1, conf->ops_total);
+ conf->ops_completed++;
+ }
}
errno = 0;
case ENOENT:
break;
default:
- return seterror(conf, "can't unlink");
+ return seterror(conf, "can't unlink %s: %s", dest, strerror(errno));
}
}
nitem.dest);
} else if (conf->progress == 1) {
/* overwrite */
- /* one dot per 2% */
- int was = 50 * conf->ops_completed / conf->ops_total;
- int now = 50 * (conf->ops_completed+1) / conf->ops_total;
- while (was++ < now) {
- fprintf(stderr, ".");
- }
+ pdots(50, '.', conf->ops_completed, conf->ops_completed + 1, conf->ops_total);
+ conf->ops_completed++;
conf->ops_completed++;
} else {
- /* one dot per 2% */
- int was = 50 * conf->ops_completed / conf->ops_total;
- int now = 50 * (conf->ops_completed+1) / conf->ops_total;
- while (was++ < now) {
- fprintf(stderr, ".");
- }
+ pdots(50, '.', conf->ops_completed, conf->ops_completed + 1, conf->ops_total);
conf->ops_completed++;
}
}
/* TODO final report function in conf var */
}
-static int count_ops(struct config *conf) {
- return zpm_db_int(conf->log, "select count(*) from syncinfo where op in ('remove', 'update', 'new')");
+static void count_ops(struct config *conf) {
+ conf->ops_remove = zpm_db_int(conf->log, "select count(*) from syncinfo where op = 'remove'");
+ conf->ops_update = zpm_db_int(conf->log, "select count(*) from syncinfo where op = 'update'");
+ conf->ops_install = zpm_db_int(conf->log, "select count(*) from syncinfo where op = 'new'");
+ conf->ops_total = conf->ops_remove + conf->ops_update + conf->ops_install;
}
int main(int ac, char **av) {
if (!conf.errors) {
conf.exitonerror = conf.dryrun ? 0 : 1;
conf.errabort = conf.dryrun ? 0 : 1;
- conf.reverse = 1;
- conf.ops_total = count_ops(&conf);
+ count_ops(&conf);
fprintf(stderr, "file ops: %d\n", conf.ops_total);
- if (conf.verbose) {
- fprintf(stderr, "removing old files\n");
- }
- runstage(&conf, "remove", remove_files);
- conf.reverse = 0;
- if (conf.verbose) {
- fprintf(stderr, "updating files\n");
+ if (conf.ops_remove > 0) {
+ if (conf.verbose) {
+ fprintf(stderr, "removing %d file%s\n", conf.ops_remove, conf.ops_remove > 0 ? "s" : "");
+ }
+ conf.reverse = 1;
+ conf.ops_completed = 0;
+ conf.ops_total = conf.ops_remove;
+ runstage(&conf, "remove", remove_files);
+ if (conf.verbose && conf.progress < 2) {
+ fprintf(stderr, " done\n");
+ fflush(stderr);
+ }
}
- runstage(&conf, "update", install_files);
- if (conf.verbose) {
- fprintf(stderr, "installing %d files\n", conf.ops_total);
+
+ if (conf.ops_update > 0) {
+ if (conf.verbose) {
+ fprintf(stderr, "updating %d file%s\n", conf.ops_update, conf.ops_update > 0 ? "s" : "");
+ }
+ conf.reverse = 0;
+ conf.ops_completed = 0;
+ conf.ops_total = conf.ops_update;
+ runstage(&conf, "update", install_files);
+ if (conf.verbose && conf.progress < 2) {
+ fprintf(stderr, " done\n");
+ fflush(stderr);
+ }
}
- runstage(&conf, "new", install_files);
- if (conf.verbose && conf.progress < 2) {
- fprintf(stderr, " done\n");
- fflush(stderr);
+
+ if (conf.ops_install > 0) {
+ if (conf.verbose) {
+ fprintf(stderr, "installing %d file%s\n", conf.ops_install, conf.ops_install > 0 ? "s" : "");
+ }
+ conf.reverse = 0;
+ conf.ops_completed = 0;
+ conf.ops_total = conf.ops_install;
+ runstage(&conf, "new", install_files);
+ if (conf.verbose && conf.progress < 2) {
+ fprintf(stderr, " done\n");
+ fflush(stderr);
+ }
}
}
}