/* Recurses opath and adds metadata entries to the metaentry list */ void mentries_recurse_path(const char *opath, struct metahash **mhash, msettings *st) { char *path = normalize_path(opath); if (!(*mhash)) *mhash = mhash_alloc(); mentries_recurse(path, *mhash, st); free(path); }
/* Recurses opath and adds metadata entries to the metaentry list */ void mentries_recurse_path(const char *opath, struct metahash **mhash, bool git) { char *path = normalize_path(opath); if (!(*mhash)) *mhash = mhash_alloc(); if (git) mentries_recurse(path, *mhash); else mentries_recurse_wo_git(path, *mhash); free(path); }
/* Creates a metaentry list from a file */ void mentries_fromfile(struct metahash **mhash, const char *path) { struct metaentry *mentry; char *mmapstart; char *ptr; char *max; int fd; struct stat sbuf; int i; if (!(*mhash)) *mhash = mhash_alloc(); fd = open(path, O_RDONLY); if (fd < 0) { msg(MSG_CRITICAL, "Failed to open %s: %s\n", path, strerror(errno)); exit(EXIT_FAILURE); } if (fstat(fd, &sbuf)) { msg(MSG_CRITICAL, "Failed to stat %s: %s\n", path, strerror(errno)); exit(EXIT_FAILURE); } if (sbuf.st_size < (SIGNATURELEN + VERSIONLEN)) { msg(MSG_CRITICAL, "File %s has an invalid size\n", path); exit(EXIT_FAILURE); } mmapstart = mmap(NULL, (size_t)sbuf.st_size, PROT_READ, MAP_SHARED, fd, 0); if (mmapstart == MAP_FAILED) { msg(MSG_CRITICAL, "Unable to mmap %s: %s\n", path, strerror(errno)); exit(EXIT_FAILURE); } ptr = mmapstart; max = mmapstart + sbuf.st_size; if (strncmp(ptr, SIGNATURE, SIGNATURELEN)) { msg(MSG_CRITICAL, "Invalid signature for file %s\n", path); goto out; } ptr += SIGNATURELEN; if (strncmp(ptr, VERSION, VERSIONLEN)) { msg(MSG_CRITICAL, "Invalid version of file %s\n", path); goto out; } ptr += VERSIONLEN; while (ptr < mmapstart + sbuf.st_size) { if (*ptr == '\0') { msg(MSG_CRITICAL, "Invalid characters in file %s\n", path); goto out; } mentry = mentry_alloc(); mentry->path = read_string(&ptr, max); mentry->pathlen = strlen(mentry->path); mentry->owner = read_string(&ptr, max); mentry->group = read_string(&ptr, max); mentry->mtime = (time_t)read_int(&ptr, 8, max); mentry->mtimensec = (time_t)read_int(&ptr, 8, max); mentry->mode = (mode_t)read_int(&ptr, 2, max); mentry->xattrs = (unsigned int)read_int(&ptr, 4, max); if (!mentry->xattrs) { mentry_insert(mentry, *mhash); continue; } mentry->xattr_names = xmalloc(mentry->xattrs * sizeof(char *)); mentry->xattr_lvalues = xmalloc(mentry->xattrs * sizeof(int)); mentry->xattr_values = xmalloc(mentry->xattrs * sizeof(char *)); for (i = 0; i < mentry->xattrs; i++) { mentry->xattr_names[i] = read_string(&ptr, max); mentry->xattr_lvalues[i] = (int)read_int(&ptr, 4, max); mentry->xattr_values[i] = read_binary_string(&ptr, mentry->xattr_lvalues[i], max); } mentry_insert(mentry, *mhash); } out: munmap(mmapstart, sbuf.st_size); close(fd); }