commit:     191df7d69bc652b5e7899d44934fea0de05aa53d
Author:     Fabian Groffen <grobian <AT> gentoo <DOT> org>
AuthorDate: Wed Nov 29 16:42:54 2017 +0000
Commit:     Fabian Groffen <grobian <AT> gentoo <DOT> org>
CommitDate: Wed Nov 29 16:42:54 2017 +0000
URL:        https://gitweb.gentoo.org/repo/proj/prefix.git/commit/?id=191df7d6

hashgen: generate GLEP 74 top level Manifest

 scripts/rsync-generation/hashgen.c | 56 ++++++++++++++++++++++++++++++++++----
 1 file changed, 50 insertions(+), 6 deletions(-)

diff --git a/scripts/rsync-generation/hashgen.c 
b/scripts/rsync-generation/hashgen.c
index 034ea7f170..4180665e0f 100644
--- a/scripts/rsync-generation/hashgen.c
+++ b/scripts/rsync-generation/hashgen.c
@@ -4,6 +4,7 @@
 #include <strings.h>
 #include <ctype.h>
 #include <dirent.h>
+#include <time.h>
 #include <errno.h>
 #include <sys/stat.h>
 #include <sys/types.h>
@@ -95,7 +96,7 @@ write_hashes(
 #pragma omp section
                        {
                                if (hashes & HASH_BLAKE2B)
-                                       blake2b_update(&bl2b, data, len);
+                                       blake2b_update(&bl2b, (unsigned char 
*)data, len);
                        }
                }
        }
@@ -152,7 +153,7 @@ write_hashes(
        len += snprintf(data + len, sizeof(data) - len, "\n");
 
        if (m != NULL)
-               fwrite(data, 1, len, m);
+               fwrite(data, len, 1, m);
        if (gm != NULL)
                gzwrite(gm, data, len);
 }
@@ -202,7 +203,7 @@ parse_layout_conf(const char *path)
 
        /* read file, examine lines after encountering a newline, that is,
         * if the file doesn't end with a newline, the final bit is ignored */
-       while (sz = fread(buf + len, 1, sizeof(buf) - len, f) > 0) {
+       while ((sz = fread(buf + len, 1, sizeof(buf) - len, f)) > 0) {
                len += sz;
                last_nl = NULL;
                for (p = buf; p - buf < len; p++) {
@@ -256,6 +257,7 @@ parse_layout_conf(const char *path)
 
 static char *str_manifest = "Manifest";
 static char *str_manifest_gz = "Manifest.gz";
+static char *str_manifest_files_gz = "Manifest.files.gz";
 static char *
 process_dir(const char *dir)
 {
@@ -296,10 +298,12 @@ process_dir(const char *dir)
                /* recurse into subdirs */
                if ((d = opendir(dir)) != NULL) {
                        struct stat s;
+                       char *my_manifest =
+                               global_manifest ? str_manifest_files_gz : 
str_manifest_gz;
 
                        /* open up a gzipped Manifest to keep the hashes of the
                         * Manifests in the subdirs */
-                       snprintf(manifest, sizeof(manifest), "%s/%s", dir, 
str_manifest_gz);
+                       snprintf(manifest, sizeof(manifest), "%s/%s", dir, 
my_manifest);
                        if ((mf = gzopen(manifest, "wb9")) == NULL) {
                                fprintf(stderr, "failed to open file '%s' for 
writing: %s\n",
                                                manifest, strerror(errno));
@@ -309,7 +313,7 @@ process_dir(const char *dir)
                        while ((e = readdir(d)) != NULL) {
                                if (e->d_name[0] == '.')
                                        continue;
-                               if (strcmp(e->d_name, str_manifest_gz) == 0)
+                               if (strcmp(e->d_name, my_manifest) == 0)
                                        continue;
                                snprintf(path, sizeof(path), "%s/%s", dir, 
e->d_name);
                                if (!stat(path, &s)) {
@@ -328,7 +332,47 @@ process_dir(const char *dir)
                        }
                        closedir(d);
 
-                       gzclose(mf);
+                       if (global_manifest) {
+                               char globmanifest[8192];
+                               char buf[2048];
+                               size_t len;
+                               FILE *m;
+                               time_t rtime;
+
+                               len = snprintf(buf, sizeof(buf),
+                                               "IGNORE distfiles\n"
+                                               "IGNORE local\n"
+                                               "IGNORE lost+found\n"
+                                               "IGNORE packages\n");
+                               gzwrite(mf, buf, len);
+                               gzclose(mf);
+
+                               /* create global Manifest */
+                               snprintf(globmanifest, sizeof(globmanifest),
+                                               "%s/%s", dir, str_manifest);
+                               if ((m = fopen(globmanifest, "w")) == NULL) {
+                                       fprintf(stderr, "failed to open file 
'%s' "
+                                                       "for writing: %s\n",
+                                                       globmanifest, 
strerror(errno));
+                                       return NULL;
+                               }
+
+                               write_hashes(dir, my_manifest, "MANIFEST", m, 
NULL);
+                               time(&rtime);
+                               len = strftime(buf, sizeof(buf),
+                                               "TIMESTAMP 
%Y-%m-%dT%H:%M:%SZ\n", gmtime(&rtime));
+                               fwrite(buf, len, 1, m);
+                               fflush(m);
+                               fclose(m);
+
+                               if (tv[0].tv_sec != 0) {
+                                       /* restore dir mtime, and set Manifest 
mtime to match it */
+                                       utimes(globmanifest, tv);
+                               }
+                       } else {
+                               gzclose(mf);
+                       }
+
                        if (tv[0].tv_sec != 0) {
                                /* restore dir mtime, and set Manifest mtime to 
match it */
                                utimes(manifest, tv);

Reply via email to