+/*
+ * To turn off use of fchown(), fchmod(), or futimes(),
+ * uncomment one or more of the following.
+ */
+//#undef HAVE_FCHOWN
+//#undef HAVE_FCHMOD
+//#undef HAVE_FUTIMES
+
+/*
+ * Print errors only if debug level defined or we are root.
+ * root should not get errors. Errors for users causes
+ * too much output.
+ */
+#define print_error(jcr) (chk_dbglvl(100) || (my_uid == 0 && (!jcr || jcr->job_uid == 0)))
+
+/*
+ * Restore the owner and permissions (mode) of a Directory.
+ * See attribs.c for the equivalent for files.
+ */
+void set_own_mod(ATTR *attr, char *path, uid_t owner, gid_t group, mode_t mode)
+{
+ if (lchown(path, owner, group) != 0 && print_error(attr->jcr)
+#ifdef AFS
+ && errno != EPERM
+#endif
+ ) {
+ berrno be;
+ Jmsg4(attr->jcr, M_WARNING, 0, _("Cannot change owner and/or group of %s: ERR=%s %d %d\n"),
+ path, be.bstrerror(), getuid(), attr->jcr->job_uid);
+ }
+ if (lchmod(path, mode) != 0 && print_error(attr->jcr)) {
+ berrno be;
+ Jmsg2(attr->jcr, M_WARNING, 0, _("Cannot change permissions of %s: ERR=%s\n"),
+ path, be.bstrerror());
+ }
+}
+
+
+bool set_mod_own_time(JCR *jcr, BFILE *ofd, ATTR *attr)
+{
+ bool ok = true;
+ struct utimbuf ut;
+
+ /* Do not try to set rights with f functions when using a plugin */
+ if (is_bopen(ofd) && !ofd->cmd_plugin) { /* TODO: Look with opt_plugin */
+ /*
+ * The #ifdefing is a bit ugly, but it is the only
+ * way we can ensure this works on older systems.
+ */
+#ifdef HAVE_FCHOWN
+ if (fchown(ofd->fid, attr->statp.st_uid, attr->statp.st_gid) < 0 && print_error(jcr)) {
+#else
+ if (lchown(attr->ofname, attr->statp.st_uid, attr->statp.st_gid) < 0 && print_error(jcr)) {
+#endif
+ berrno be;
+ Jmsg2(jcr, M_ERROR, 0, _("Unable to set file owner %s: ERR=%s\n"),
+ attr->ofname, be.bstrerror());
+ ok = false;
+ }
+
+#ifdef HAVE_FCHMOD
+ if (fchmod(ofd->fid, attr->statp.st_mode) < 0 && print_error(jcr)) {
+#else
+ if (lchmod(attr->ofname, attr->statp.st_mode) < 0 && print_error(jcr)) {
+#endif
+ berrno be;
+ Jmsg2(jcr, M_ERROR, 0, _("Unable to set file modes %s: ERR=%s\n"),
+ attr->ofname, be.bstrerror());
+ ok = false;
+ }
+
+#ifdef HAVE_FUTIMES
+ struct timeval times[2];
+ times[0].tv_sec = attr->statp.st_atime;
+ times[0].tv_usec = 0;
+ times[1].tv_sec = attr->statp.st_mtime;
+ times[1].tv_usec = 0;
+ if (futimes(ofd->fid, times) < 0 && print_error(jcr)) {
+#else
+ ut.actime = attr->statp.st_atime;
+ ut.modtime = attr->statp.st_mtime;
+ //bclose(ofd);
+ if (utime(attr->ofname, &ut) < 0 && print_error(jcr)) {
+#endif
+ berrno be;
+ Jmsg2(jcr, M_ERROR, 0, _("Unable to set file times %s: ERR=%s\n"),
+ attr->ofname, be.bstrerror());
+ ok = false;
+ }
+ } else {
+ if (lchown(attr->ofname, attr->statp.st_uid, attr->statp.st_gid) < 0 && print_error(jcr)) {
+ berrno be;
+ Jmsg2(jcr, M_ERROR, 0, _("Unable to set file owner %s: ERR=%s\n"),
+ attr->ofname, be.bstrerror());
+ ok = false;
+ }
+ if (lchmod(attr->ofname, attr->statp.st_mode) < 0 && print_error(jcr)) {
+ berrno be;
+ Jmsg2(jcr, M_ERROR, 0, _("Unable to set file modes %s: ERR=%s\n"),
+ attr->ofname, be.bstrerror());
+ ok = false;
+ }
+ /*
+ * Reset file times.
+ */
+ ut.actime = attr->statp.st_atime;
+ ut.modtime = attr->statp.st_mtime;
+
+ if (utime(attr->ofname, &ut) < 0 && print_error(jcr)) {
+ berrno be;
+ Jmsg2(jcr, M_ERROR, 0, _("Unable to set file times %s: ERR=%s\n"),
+ attr->ofname, be.bstrerror());
+ ok = false;
+ }
+ }
+ return ok;
+}
+
+/*