iRewrite dedup from scratch - dedup - deduplicating backup program Err bitreich.org 70 hgit clone git://bitreich.org/dedup/ git://enlrupgkhuxnvlhsf6lc3fziv5h2hhfrinws65d7roiv6bfj7d652fid.onion/dedup/ URL:git://bitreich.org/dedup/ git://enlrupgkhuxnvlhsf6lc3fziv5h2hhfrinws65d7roiv6bfj7d652fid.onion/dedup/ bitreich.org 70 1Log /scm/dedup/log.gph bitreich.org 70 1Files /scm/dedup/files.gph bitreich.org 70 1Refs /scm/dedup/refs.gph bitreich.org 70 1Tags /scm/dedup/tag bitreich.org 70 1README /scm/dedup/file/README.gph bitreich.org 70 1LICENSE /scm/dedup/file/LICENSE.gph bitreich.org 70 i--- Err bitreich.org 70 1commit 54776ab6b2b26aea19f77b7876e80cff4b602913 /scm/dedup/commit/54776ab6b2b26aea19f77b7876e80cff4b602913.gph bitreich.org 70 1parent 3d79ba2671de814d94474dce3765be64a982cc5a /scm/dedup/commit/3d79ba2671de814d94474dce3765be64a982cc5a.gph bitreich.org 70 hAuthor: sin URL:mailto:sin@2f30.org bitreich.org 70 iDate: Thu, 25 Apr 2019 13:05:40 +0100 Err bitreich.org 70 i Err bitreich.org 70 iRewrite dedup from scratch Err bitreich.org 70 i Err bitreich.org 70 iThe new design provides 3 abstractions. Err bitreich.org 70 i Err bitreich.org 70 i * The snapshot layer Err bitreich.org 70 i * The block layer Err bitreich.org 70 i * The chunker interface Err bitreich.org 70 i Err bitreich.org 70 iThe snapshot layer manages snapshots. A snapshot is a collection of Err bitreich.org 70 iblock hashes. Each snapshot is a separate file in /archive/. Err bitreich.org 70 iThe name of the snapshot file is selected by the user. Err bitreich.org 70 i Err bitreich.org 70 iThe block layer is composed of 3 sub-layers. Err bitreich.org 70 i Err bitreich.org 70 i * Generic layer Err bitreich.org 70 i * Compression layer Err bitreich.org 70 i * Storage layer Err bitreich.org 70 i Err bitreich.org 70 iThe generic layer provides the top-level block interface and deals Err bitreich.org 70 iwith user provided buffers. When a write goes through the generic Err bitreich.org 70 ilayer it is passed down to the compression layer which compresses the Err bitreich.org 70 ipayload, prepends a compression descriptor and passes it down to the Err bitreich.org 70 istorage layer. Err bitreich.org 70 i Err bitreich.org 70 iThe storage layer hashes the payload and prepends a storage Err bitreich.org 70 idescriptor. The final buffer is written to the storage file. The Err bitreich.org 70 istorage layer also maintains a cache of hashes which is used to Err bitreich.org 70 idetermine if a block exists in the storage or not. Err bitreich.org 70 i Err bitreich.org 70 iThe chunker interface is basically unchanged. Err bitreich.org 70 i Err bitreich.org 70 iDiffstat: Err bitreich.org 70 i M Makefile | 115 ++++++------------------------- Err bitreich.org 70 i M README | 25 ++++++++----------------- Err bitreich.org 70 i M TODO | 1 - Err bitreich.org 70 i A bcompress.c | 260 +++++++++++++++++++++++++++++++ Err bitreich.org 70 i D blake2bp-ref.c | 359 ------------------------------- Err bitreich.org 70 i D blake2s-ref.c | 367 ------------------------------ Err bitreich.org 70 i D blake2sp-ref.c | 359 ------------------------------- Err bitreich.org 70 i A block.c | 114 +++++++++++++++++++++++++++++++ Err bitreich.org 70 i A block.h | 34 +++++++++++++++++++++++++++++++ Err bitreich.org 70 i A bstorage.c | 564 +++++++++++++++++++++++++++++++ Err bitreich.org 70 i M chunker.c | 174 +++++++++++++++++-------------- Err bitreich.org 70 i A chunker.h | 8 ++++++++ Err bitreich.org 70 i D compress-lz4.c | 54 ------------------------------- Err bitreich.org 70 i D compress-none.c | 41 ------------------------------- Err bitreich.org 70 i D compress-snappy.c | 54 ------------------------------- Err bitreich.org 70 i D compress.c | 112 ------------------------------- Err bitreich.org 70 i M config.h | 11 +++++++---- Err bitreich.org 70 i M config.mk | 5 +++-- Err bitreich.org 70 i D dedup.h | 233 ------------------------------- Err bitreich.org 70 i D dup-check.1 | 25 ------------------------- Err bitreich.org 70 i D dup-check.c | 157 ------------------------------- Err bitreich.org 70 i D dup-info.1 | 37 ------------------------------- Err bitreich.org 70 i D dup-info.c | 141 ------------------------------- Err bitreich.org 70 i M dup-init.1 | 6 +++--- Err bitreich.org 70 i M dup-init.c | 83 ++++++------------------------- Err bitreich.org 70 i D dup-list.1 | 25 ------------------------- Err bitreich.org 70 i D dup-list.c | 113 ------------------------------- Err bitreich.org 70 i D dup-migrate | 28 ---------------------------- Err bitreich.org 70 i D dup-migrate.1 | 26 -------------------------- Err bitreich.org 70 i M dup-pack.1 | 20 ++++++++++---------- Err bitreich.org 70 i M dup-pack.c | 228 +++++++------------------------ Err bitreich.org 70 i M dup-unpack.1 | 17 ++++++++--------- Err bitreich.org 70 i M dup-unpack.c | 170 +++++++++++++------------------ Err bitreich.org 70 i D hash-blake2b.c | 26 -------------------------- Err bitreich.org 70 i D hash-blake2bp.c | 26 -------------------------- Err bitreich.org 70 i D hash-blake2s.c | 26 -------------------------- Err bitreich.org 70 i D hash-blake2sp.c | 26 -------------------------- Err bitreich.org 70 i D hash.c | 94 ------------------------------- Err bitreich.org 70 i D icache.c | 114 ------------------------------- Err bitreich.org 70 i A queue.h | 534 +++++++++++++++++++++++++++++++ Err bitreich.org 70 i A snap.c | 249 +++++++++++++++++++++++++++++++ Err bitreich.org 70 i A snap.h | 8 ++++++++ Err bitreich.org 70 i D types.c | 192 ------------------------------- Err bitreich.org 70 i D utils.c | 288 ------------------------------- Err bitreich.org 70 i Err bitreich.org 70 i44 files changed, 2063 insertions(+), 3486 deletions(-) Err bitreich.org 70 i--- Err bitreich.org 70 1diff --git a/Makefile b/Makefile /scm/dedup/file/Makefile.gph bitreich.org 70 i@@ -1,143 +1,68 @@ Err bitreich.org 70 i include config.mk Err bitreich.org 70 i Err bitreich.org 70 i-VERSION = 1.0 Err bitreich.org 70 i-PREFIX = /usr/local Err bitreich.org 70 i-MANPREFIX = $(PREFIX)/man Err bitreich.org 70 i-BIN = dup-check dup-info dup-init dup-list dup-pack dup-unpack Err bitreich.org 70 i-SCRIPTS = dup-migrate Err bitreich.org 70 i- Err bitreich.org 70 i-MAN = \ Err bitreich.org 70 i- dup-check.1 \ Err bitreich.org 70 i- dup-info.1 \ Err bitreich.org 70 i- dup-init.1 \ Err bitreich.org 70 i- dup-list.1 \ Err bitreich.org 70 i- dup-migrate.1 \ Err bitreich.org 70 i- dup-pack.1 \ Err bitreich.org 70 i- dup-unpack.1 \ Err bitreich.org 70 i+BIN = dup-init dup-pack dup-unpack Err bitreich.org 70 i+ Err bitreich.org 70 i+MAN = dup-init.1 dup-pack.1 dup-unpack.1 Err bitreich.org 70 i Err bitreich.org 70 i HDR = \ Err bitreich.org 70 i arg.h \ Err bitreich.org 70 i blake2-impl.h \ Err bitreich.org 70 i blake2.h \ Err bitreich.org 70 i+ block.h \ Err bitreich.org 70 i+ chunker.h \ Err bitreich.org 70 i config.h \ Err bitreich.org 70 i- dedup.h \ Err bitreich.org 70 i+ queue.h \ Err bitreich.org 70 i+ snap.h \ Err bitreich.org 70 i tree.h \ Err bitreich.org 70 i Err bitreich.org 70 i-SRC = \ Err bitreich.org 70 i- $(HDR) \ Err bitreich.org 70 i- blake2b-ref.c \ Err bitreich.org 70 i- blake2bp-ref.c \ Err bitreich.org 70 i- blake2s-ref.c \ Err bitreich.org 70 i- blake2sp-ref.c \ Err bitreich.org 70 i- chunker.c \ Err bitreich.org 70 i- compress-lz4.c \ Err bitreich.org 70 i- compress-none.c \ Err bitreich.org 70 i- compress-snappy.c \ Err bitreich.org 70 i- compress.c \ Err bitreich.org 70 i- dup-check.c \ Err bitreich.org 70 i- dup-info.c \ Err bitreich.org 70 i- dup-init.c \ Err bitreich.org 70 i- dup-list.c \ Err bitreich.org 70 i- dup-pack.c \ Err bitreich.org 70 i- dup-unpack.c \ Err bitreich.org 70 i- hash-blake2b.c \ Err bitreich.org 70 i- hash-blake2bp.c \ Err bitreich.org 70 i- hash-blake2s.c \ Err bitreich.org 70 i- hash-blake2sp.c \ Err bitreich.org 70 i- hash.c \ Err bitreich.org 70 i- icache.c \ Err bitreich.org 70 i- pack.c \ Err bitreich.org 70 i- types.c \ Err bitreich.org 70 i- unpack.c \ Err bitreich.org 70 i- utils.c \ Err bitreich.org 70 i- Err bitreich.org 70 i COMMOBJ = \ Err bitreich.org 70 i+ bcompress.o \ Err bitreich.org 70 i blake2b-ref.o \ Err bitreich.org 70 i- blake2bp-ref.o \ Err bitreich.org 70 i- blake2s-ref.o \ Err bitreich.org 70 i- blake2sp-ref.o \ Err bitreich.org 70 i+ block.o \ Err bitreich.org 70 i+ bstorage.o \ Err bitreich.org 70 i chunker.o \ Err bitreich.org 70 i- compress-lz4.o \ Err bitreich.org 70 i- compress-none.o \ Err bitreich.org 70 i- compress-snappy.o \ Err bitreich.org 70 i- compress.o \ Err bitreich.org 70 i- hash-blake2b.o \ Err bitreich.org 70 i- hash-blake2bp.o \ Err bitreich.org 70 i- hash-blake2s.o \ Err bitreich.org 70 i- hash-blake2sp.o \ Err bitreich.org 70 i- hash.o \ Err bitreich.org 70 i- icache.o \ Err bitreich.org 70 i pack.o \ Err bitreich.org 70 i- types.o \ Err bitreich.org 70 i+ snap.o \ Err bitreich.org 70 i unpack.o \ Err bitreich.org 70 i- utils.o \ Err bitreich.org 70 i Err bitreich.org 70 i-DCHECKOBJ = $(COMMOBJ) dup-check.o Err bitreich.org 70 i-DINFOOBJ = $(COMMOBJ) dup-info.o Err bitreich.org 70 i DINITOBJ = $(COMMOBJ) dup-init.o Err bitreich.org 70 i-DLISTOBJ = $(COMMOBJ) dup-list.o Err bitreich.org 70 i DPACKOBJ = $(COMMOBJ) dup-pack.o Err bitreich.org 70 i DUNPACKOBJ = $(COMMOBJ) dup-unpack.o Err bitreich.org 70 i Err bitreich.org 70 i-DISTFILES = \ Err bitreich.org 70 i- $(MAN) \ Err bitreich.org 70 i- $(SRC) \ Err bitreich.org 70 i- $(SCRIPTS) \ Err bitreich.org 70 i- CHANGELOG \ Err bitreich.org 70 i- LICENSE \ Err bitreich.org 70 i- Makefile \ Err bitreich.org 70 i- README \ Err bitreich.org 70 i- config.mk \ Err bitreich.org 70 i- Err bitreich.org 70 i-CFLAGS = -g -O2 -Wall $(OPENMPCFLAGS) Err bitreich.org 70 i-CPPFLAGS = -I/usr/local/include -D_FILE_OFFSET_BITS=64 Err bitreich.org 70 i-LDFLAGS = -L/usr/local/lib Err bitreich.org 70 i-LDLIBS = -llz4 -lsnappy $(OPENMPLDLIBS) Err bitreich.org 70 i+CPPFLAGS = -D_FILE_OFFSET_BITS=64 Err bitreich.org 70 i+LDLIBS = -llz4 -lsnappy Err bitreich.org 70 i Err bitreich.org 70 i all: $(BIN) Err bitreich.org 70 i Err bitreich.org 70 i-$(DCHECKOBJ) $(DINFOOBJ) $(DINITOBJ) $(DLISTOBJ) $(DPACKOBJ) $(DUNPACKOBJ): $(HDR) Err bitreich.org 70 i+$(DINITOBJ) $(DPACKOBJ) $(DUNPACKOBJ): $(HDR) Err bitreich.org 70 i Err bitreich.org 70 i clean: Err bitreich.org 70 i- rm -f $(DCHECKOBJ) $(DINFOOBJ) $(DINITOBJ) $(DLISTOBJ) $(DPACKOBJ) $(DUNPACKOBJ) $(BIN) dedup-$(VERSION).tar.gz Err bitreich.org 70 i+ rm -f $(DINITOBJ) $(DPACKOBJ) $(DUNPACKOBJ) $(BIN) Err bitreich.org 70 i+ rm -rf dedup-$(VERSION) dedup-$(VERSION).tar.gz Err bitreich.org 70 i Err bitreich.org 70 i install: all Err bitreich.org 70 i mkdir -p $(DESTDIR)$(PREFIX)/bin Err bitreich.org 70 i cp -f $(BIN) $(DESTDIR)$(PREFIX)/bin Err bitreich.org 70 i- cp -f $(SCRIPTS) $(DESTDIR)$(PREFIX)/bin Err bitreich.org 70 i mkdir -p $(DESTDIR)$(MANPREFIX)/man1 Err bitreich.org 70 i cp -f $(MAN) $(DESTDIR)$(MANPREFIX)/man1 Err bitreich.org 70 i Err bitreich.org 70 i uninstall: Err bitreich.org 70 i- cd $(DESTDIR)$(PREFIX)/bin && rm -f $(BIN) $(SCRIPTS) Err bitreich.org 70 i+ cd $(DESTDIR)$(PREFIX)/bin && rm -f $(BIN) Err bitreich.org 70 i cd $(DESTDIR)$(MANPREFIX)/man1 && rm -f $(MAN) Err bitreich.org 70 i Err bitreich.org 70 i-dist: Err bitreich.org 70 i+dist: clean Err bitreich.org 70 i mkdir -p dedup-$(VERSION) Err bitreich.org 70 i- cp $(DISTFILES) dedup-$(VERSION) Err bitreich.org 70 i- tar -cf dedup-$(VERSION).tar dedup-$(VERSION) Err bitreich.org 70 i- gzip dedup-$(VERSION).tar Err bitreich.org 70 i- rm -rf dedup-$(VERSION) Err bitreich.org 70 i- Err bitreich.org 70 i-.PHONY: all clean install uninstall dist Err bitreich.org 70 i+ cp `find . -maxdepth 1 -type f` dedup-$(VERSION) Err bitreich.org 70 i+ tar -cf - dedup-$(VERSION) | gzip > dedup-$(VERSION).tar.gz Err bitreich.org 70 i Err bitreich.org 70 i .SUFFIXES: .c .o Err bitreich.org 70 i Err bitreich.org 70 i .c.o: Err bitreich.org 70 i $(CC) $(CPPFLAGS) $(CFLAGS) -c $< Err bitreich.org 70 i Err bitreich.org 70 i-dup-check: $(DCHECKOBJ) Err bitreich.org 70 i- $(CC) -o $@ $(DCHECKOBJ) $(LDFLAGS) $(LDLIBS) Err bitreich.org 70 i- Err bitreich.org 70 i-dup-info: $(DINFOOBJ) Err bitreich.org 70 i- $(CC) -o $@ $(DINFOOBJ) $(LDFLAGS) $(LDLIBS) Err bitreich.org 70 i- Err bitreich.org 70 i dup-init: $(DINITOBJ) Err bitreich.org 70 i $(CC) -o $@ $(DINITOBJ) $(LDFLAGS) $(LDLIBS) Err bitreich.org 70 i Err bitreich.org 70 i-dup-list: $(DLISTOBJ) Err bitreich.org 70 i- $(CC) -o $@ $(DLISTOBJ) $(LDFLAGS) $(LDLIBS) Err bitreich.org 70 i- Err bitreich.org 70 i dup-pack: $(DPACKOBJ) Err bitreich.org 70 i $(CC) -o $@ $(DPACKOBJ) $(LDFLAGS) $(LDLIBS) Err bitreich.org 70 i Err bitreich.org 70 1diff --git a/README b/README /scm/dedup/file/README.gph bitreich.org 70 i@@ -6,32 +6,25 @@ dedup is a simple data deduplication program. Err bitreich.org 70 i Getting started Err bitreich.org 70 i =============== Err bitreich.org 70 i Err bitreich.org 70 i-To use dedup you have to first initialize the repository. Err bitreich.org 70 i+To use dedup you have to first initialize the repository: Err bitreich.org 70 i Err bitreich.org 70 i dup-init repo Err bitreich.org 70 i Err bitreich.org 70 i-This will create .{snapshots,store} files in the repo directory. The Err bitreich.org 70 i-store file contains all the unique blocks. The snapshots file Err bitreich.org 70 i-contains all the revisions of files that have been deduplicated. Err bitreich.org 70 i+dup-init(1) will create a storage file and an archive directory inside Err bitreich.org 70 i+the repository. The storage file contains all the unique blocks of Err bitreich.org 70 i+the repository. The archive directory contains the snapshots. Err bitreich.org 70 i Err bitreich.org 70 i dedup only handles a single file at a time, so using tar is advised. Err bitreich.org 70 i For example, to dedup a directory tree you can invoke dup-pack(1) as Err bitreich.org 70 i follows: Err bitreich.org 70 i Err bitreich.org 70 i- tar -c ~/dir | dup-pack -m "$(date)" repo Err bitreich.org 70 i+ tar -c ~/dir | dup-pack -r repo foo Err bitreich.org 70 i Err bitreich.org 70 i-The -m flag is used to attach an arbitrary message to the snapshot. Err bitreich.org 70 i+This will create a new snapshot called foo under repo/archive/. Err bitreich.org 70 i Err bitreich.org 70 i-To list all known revisions run: Err bitreich.org 70 i+To extract a snapshot: Err bitreich.org 70 i Err bitreich.org 70 i- dup-list repo Err bitreich.org 70 i- Err bitreich.org 70 i-You will get a list of hashes. Each hash corresponds to a single file Err bitreich.org 70 i-(in this case, a tar archive). Err bitreich.org 70 i- Err bitreich.org 70 i-To extract a file from the deduplicated store run: Err bitreich.org 70 i- Err bitreich.org 70 i- dup-unpack repo > snapshot.tar Err bitreich.org 70 i+ dup-unpack -r repo foo > dir.tar Err bitreich.org 70 i Err bitreich.org 70 i Portability Err bitreich.org 70 i =========== Err bitreich.org 70 i@@ -41,9 +34,7 @@ dedup works on Linux, *BSD, macOS and possibly other UNIX-like systems. Err bitreich.org 70 i Dependencies Err bitreich.org 70 i ============ Err bitreich.org 70 i Err bitreich.org 70 i- - liblz4 Err bitreich.org 70 i - snappy Err bitreich.org 70 i- - libgomp (optional, see config.mk) Err bitreich.org 70 i Err bitreich.org 70 i Contact Err bitreich.org 70 i ======= Err bitreich.org 70 1diff --git a/TODO b/TODO /scm/dedup/file/TODO.gph bitreich.org 70 i@@ -1,4 +1,3 @@ Err bitreich.org 70 i Use a ring buffer in the chunker (avoid memmove() call) Err bitreich.org 70 i Create a library archive out of the blake2b files and link with it Err bitreich.org 70 i pledge/unveil support Err bitreich.org 70 i-Create libdedup Err bitreich.org 70 1diff --git a/bcompress.c b/bcompress.c /scm/dedup/file/bcompress.c.gph bitreich.org 70 i@@ -0,0 +1,260 @@ Err bitreich.org 70 i+/* Compression layer implementation */ Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+ Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+ Err bitreich.org 70 i+#include Err bitreich.org 70 i+ Err bitreich.org 70 i+#include "block.h" Err bitreich.org 70 i+ Err bitreich.org 70 i+#define CDNONETYPE 0x200 Err bitreich.org 70 i+#define CDSNAPPYTYPE 0x201 Err bitreich.org 70 i+#define CDSIZE (8 + 8) Err bitreich.org 70 i+ Err bitreich.org 70 i+extern int pack(unsigned char *dst, char *fmt, ...); Err bitreich.org 70 i+extern int unpack(unsigned char *src, char *fmt, ...); Err bitreich.org 70 i+ Err bitreich.org 70 i+static int bccreat(struct bctx *bctx, char *path, int mode, struct bparam *bpar); Err bitreich.org 70 i+static int bcopen(struct bctx *bctx, char *path, int flags, int mode, struct bparam *bpar); Err bitreich.org 70 i+static int bcput(struct bctx *bctx, void *buf, size_t n, unsigned char *md); Err bitreich.org 70 i+static int bcget(struct bctx *bctx, unsigned char *md, void *buf, size_t *n); Err bitreich.org 70 i+static int bcsync(struct bctx *bctx); Err bitreich.org 70 i+static int bcclose(struct bctx *bctx); Err bitreich.org 70 i+ Err bitreich.org 70 i+static struct bops bops = { Err bitreich.org 70 i+ .creat = bccreat, Err bitreich.org 70 i+ .open = bcopen, Err bitreich.org 70 i+ .put = bcput, Err bitreich.org 70 i+ .get = bcget, Err bitreich.org 70 i+ .sync = bcsync, Err bitreich.org 70 i+ .close = bcclose, Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+struct cctx { Err bitreich.org 70 i+ uint64_t type; Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Compression descriptor */ Err bitreich.org 70 i+struct cd { Err bitreich.org 70 i+ uint64_t type; Err bitreich.org 70 i+ uint64_t size; Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Read compression descriptor */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+unpackcd(void *buf, struct cd *cd) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ int n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ n = unpack(buf, "qq", Err bitreich.org 70 i+ &cd->type, Err bitreich.org 70 i+ &cd->size); Err bitreich.org 70 i+ Err bitreich.org 70 i+ assert(n == CDSIZE); Err bitreich.org 70 i+ return n; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Write compression descriptor */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+packcd(void *buf, struct cd *cd) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ int n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ n = pack(buf, "qq", Err bitreich.org 70 i+ cd->type, Err bitreich.org 70 i+ cd->size); Err bitreich.org 70 i+ Err bitreich.org 70 i+ assert(n == CDSIZE); Err bitreich.org 70 i+ return n; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bccreat(struct bctx *bctx, char *path, int mode, struct bparam *bpar) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct cctx *cctx; Err bitreich.org 70 i+ struct bops *bops; Err bitreich.org 70 i+ int type; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (strcmp(bpar->calgo, "none") == 0) Err bitreich.org 70 i+ type = CDNONETYPE; Err bitreich.org 70 i+ else if (strcmp(bpar->calgo, "snappy") == 0) Err bitreich.org 70 i+ type = CDSNAPPYTYPE; Err bitreich.org 70 i+ else Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bctx->cctx = calloc(1, sizeof(struct cctx)); Err bitreich.org 70 i+ if (bctx->cctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ cctx = bctx->cctx; Err bitreich.org 70 i+ cctx->type = type; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bops = bstorageops(); Err bitreich.org 70 i+ if (bops->creat(bctx, path, mode, bpar) < 0) { Err bitreich.org 70 i+ free(cctx); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bcopen(struct bctx *bctx, char *path, int flags, int mode, struct bparam *bpar) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct cctx *cctx; Err bitreich.org 70 i+ struct bops *bops; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bctx->cctx = calloc(1, sizeof(struct cctx)); Err bitreich.org 70 i+ if (bctx->cctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ cctx = bctx->cctx; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bops = bstorageops(); Err bitreich.org 70 i+ if (bops->open(bctx, path, flags, mode, bpar) < 0) { Err bitreich.org 70 i+ free(cctx); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (strcmp(bpar->calgo, "none") == 0) Err bitreich.org 70 i+ cctx->type = CDNONETYPE; Err bitreich.org 70 i+ else if (strcmp(bpar->calgo, "snappy") == 0) Err bitreich.org 70 i+ cctx->type = CDSNAPPYTYPE; Err bitreich.org 70 i+ else { Err bitreich.org 70 i+ bops->close(bctx); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bcput(struct bctx *bctx, void *buf, size_t n, unsigned char *md) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct cctx *cctx; Err bitreich.org 70 i+ struct bops *bops; Err bitreich.org 70 i+ struct cd cd; Err bitreich.org 70 i+ char *cbuf; Err bitreich.org 70 i+ size_t cn; Err bitreich.org 70 i+ Err bitreich.org 70 i+ cctx = bctx->cctx; Err bitreich.org 70 i+ switch (cctx->type) { Err bitreich.org 70 i+ case CDNONETYPE: Err bitreich.org 70 i+ cn = n; Err bitreich.org 70 i+ cbuf = malloc(CDSIZE + cn); Err bitreich.org 70 i+ if (cbuf == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ memcpy(&cbuf[CDSIZE], buf, cn); Err bitreich.org 70 i+ break; Err bitreich.org 70 i+ case CDSNAPPYTYPE: Err bitreich.org 70 i+ cn = snappy_max_compressed_length(n); Err bitreich.org 70 i+ cbuf = malloc(CDSIZE + cn); Err bitreich.org 70 i+ if (cbuf == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ if (snappy_compress(buf, n, &cbuf[CDSIZE], &cn) != SNAPPY_OK) { Err bitreich.org 70 i+ free(cbuf); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ break; Err bitreich.org 70 i+ default: Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ /* Prepend compression descriptor */ Err bitreich.org 70 i+ cd.type = cctx->type; Err bitreich.org 70 i+ cd.size = cn; Err bitreich.org 70 i+ packcd(cbuf, &cd); Err bitreich.org 70 i+ Err bitreich.org 70 i+ bops = bstorageops(); Err bitreich.org 70 i+ if (bops->put(bctx, cbuf, CDSIZE + cn, md) < 0) { Err bitreich.org 70 i+ free(cbuf); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ free(cbuf); Err bitreich.org 70 i+ return cd.size; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bcget(struct bctx *bctx, unsigned char *md, void *buf, size_t *n) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct bops *bops; Err bitreich.org 70 i+ struct cd cd; Err bitreich.org 70 i+ char *cbuf; Err bitreich.org 70 i+ size_t cn, un, size; Err bitreich.org 70 i+ Err bitreich.org 70 i+ size = *n; Err bitreich.org 70 i+ cn = snappy_max_compressed_length(size); Err bitreich.org 70 i+ if (cn > size) Err bitreich.org 70 i+ size = cn; Err bitreich.org 70 i+ size += CDSIZE; Err bitreich.org 70 i+ cbuf = malloc(size); Err bitreich.org 70 i+ if (cbuf == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bops = bstorageops(); Err bitreich.org 70 i+ if (bops->get(bctx, md, cbuf, &size) < 0) { Err bitreich.org 70 i+ free(cbuf); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ unpackcd(cbuf, &cd); Err bitreich.org 70 i+ switch (cd.type) { Err bitreich.org 70 i+ case CDNONETYPE: Err bitreich.org 70 i+ un = cd.size; Err bitreich.org 70 i+ if (*n < un) { Err bitreich.org 70 i+ free(cbuf); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ memcpy(buf, &cbuf[CDSIZE], un); Err bitreich.org 70 i+ break; Err bitreich.org 70 i+ case CDSNAPPYTYPE: Err bitreich.org 70 i+ if (snappy_uncompressed_length(&cbuf[CDSIZE], cd.size, Err bitreich.org 70 i+ &un) != SNAPPY_OK || *n < un) { Err bitreich.org 70 i+ free(cbuf); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (snappy_uncompress(&cbuf[CDSIZE], cd.size, buf, Err bitreich.org 70 i+ &un) != SNAPPY_OK) { Err bitreich.org 70 i+ free(cbuf); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ break; Err bitreich.org 70 i+ default: Err bitreich.org 70 i+ free(cbuf); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ free(cbuf); Err bitreich.org 70 i+ *n = un; Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bcsync(struct bctx *bctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct bops *bops = bstorageops(); Err bitreich.org 70 i+ Err bitreich.org 70 i+ return bops->sync(bctx); Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bcclose(struct bctx *bctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct cctx *cctx = bctx->cctx; Err bitreich.org 70 i+ struct bops *bops; Err bitreich.org 70 i+ Err bitreich.org 70 i+ free(cctx); Err bitreich.org 70 i+ bops = bstorageops(); Err bitreich.org 70 i+ return bops->close(bctx); Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+struct bops * Err bitreich.org 70 i+bcompressops(void) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ return &bops; Err bitreich.org 70 i+} Err bitreich.org 70 1diff --git a/blake2bp-ref.c b/blake2bp-ref.c /scm/dedup/file/blake2bp-ref.c.gph bitreich.org 70 i@@ -1,359 +0,0 @@ Err bitreich.org 70 i-/* Err bitreich.org 70 i- BLAKE2 reference source code package - reference C implementations Err bitreich.org 70 i- Err bitreich.org 70 i- Copyright 2012, Samuel Neves . You may use this under the Err bitreich.org 70 i- terms of the CC0, the OpenSSL Licence, or the Apache Public License 2.0, at Err bitreich.org 70 i- your option. The terms of these licenses can be found at: Err bitreich.org 70 i- Err bitreich.org 70 i- - CC0 1.0 Universal : http://creativecommons.org/publicdomain/zero/1.0 Err bitreich.org 70 i- - OpenSSL license : https://www.openssl.org/source/license.html Err bitreich.org 70 i- - Apache 2.0 : http://www.apache.org/licenses/LICENSE-2.0 Err bitreich.org 70 i- Err bitreich.org 70 i- More information about the BLAKE2 hash function can be found at Err bitreich.org 70 i- https://blake2.net. Err bitreich.org 70 i-*/ Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#if defined(_OPENMP) Err bitreich.org 70 i-#include Err bitreich.org 70 i-#endif Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "blake2-impl.h" Err bitreich.org 70 i- Err bitreich.org 70 i-#define PARALLELISM_DEGREE 4 Err bitreich.org 70 i- Err bitreich.org 70 i-/* Err bitreich.org 70 i- blake2b_init_param defaults to setting the expecting output length Err bitreich.org 70 i- from the digest_length parameter block field. Err bitreich.org 70 i- Err bitreich.org 70 i- In some cases, however, we do not want this, as the output length Err bitreich.org 70 i- of these instances is given by inner_length instead. Err bitreich.org 70 i-*/ Err bitreich.org 70 i-static int blake2bp_init_leaf_param( blake2b_state *S, const blake2b_param *P ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- int err = blake2b_init_param(S, P); Err bitreich.org 70 i- S->outlen = P->inner_length; Err bitreich.org 70 i- return err; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static int blake2bp_init_leaf( blake2b_state *S, size_t outlen, size_t keylen, uint64_t offset ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- blake2b_param P[1]; Err bitreich.org 70 i- P->digest_length = (uint8_t)outlen; Err bitreich.org 70 i- P->key_length = (uint8_t)keylen; Err bitreich.org 70 i- P->fanout = PARALLELISM_DEGREE; Err bitreich.org 70 i- P->depth = 2; Err bitreich.org 70 i- store32( &P->leaf_length, 0 ); Err bitreich.org 70 i- store32( &P->node_offset, offset ); Err bitreich.org 70 i- store32( &P->xof_length, 0 ); Err bitreich.org 70 i- P->node_depth = 0; Err bitreich.org 70 i- P->inner_length = BLAKE2B_OUTBYTES; Err bitreich.org 70 i- memset( P->reserved, 0, sizeof( P->reserved ) ); Err bitreich.org 70 i- memset( P->salt, 0, sizeof( P->salt ) ); Err bitreich.org 70 i- memset( P->personal, 0, sizeof( P->personal ) ); Err bitreich.org 70 i- return blake2bp_init_leaf_param( S, P ); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static int blake2bp_init_root( blake2b_state *S, size_t outlen, size_t keylen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- blake2b_param P[1]; Err bitreich.org 70 i- P->digest_length = (uint8_t)outlen; Err bitreich.org 70 i- P->key_length = (uint8_t)keylen; Err bitreich.org 70 i- P->fanout = PARALLELISM_DEGREE; Err bitreich.org 70 i- P->depth = 2; Err bitreich.org 70 i- store32( &P->leaf_length, 0 ); Err bitreich.org 70 i- store32( &P->node_offset, 0 ); Err bitreich.org 70 i- store32( &P->xof_length, 0 ); Err bitreich.org 70 i- P->node_depth = 1; Err bitreich.org 70 i- P->inner_length = BLAKE2B_OUTBYTES; Err bitreich.org 70 i- memset( P->reserved, 0, sizeof( P->reserved ) ); Err bitreich.org 70 i- memset( P->salt, 0, sizeof( P->salt ) ); Err bitreich.org 70 i- memset( P->personal, 0, sizeof( P->personal ) ); Err bitreich.org 70 i- return blake2b_init_param( S, P ); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2bp_init( blake2bp_state *S, size_t outlen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if( !outlen || outlen > BLAKE2B_OUTBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- memset( S->buf, 0, sizeof( S->buf ) ); Err bitreich.org 70 i- S->buflen = 0; Err bitreich.org 70 i- S->outlen = outlen; Err bitreich.org 70 i- Err bitreich.org 70 i- if( blake2bp_init_root( S->R, outlen, 0 ) < 0 ) Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- if( blake2bp_init_leaf( S->S[i], outlen, 0, i ) < 0 ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- S->R->last_node = 1; Err bitreich.org 70 i- S->S[PARALLELISM_DEGREE - 1]->last_node = 1; Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2bp_init_key( blake2bp_state *S, size_t outlen, const void *key, size_t keylen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if( !outlen || outlen > BLAKE2B_OUTBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if( !key || !keylen || keylen > BLAKE2B_KEYBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- memset( S->buf, 0, sizeof( S->buf ) ); Err bitreich.org 70 i- S->buflen = 0; Err bitreich.org 70 i- S->outlen = outlen; Err bitreich.org 70 i- Err bitreich.org 70 i- if( blake2bp_init_root( S->R, outlen, keylen ) < 0 ) Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- if( blake2bp_init_leaf( S->S[i], outlen, keylen, i ) < 0 ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- S->R->last_node = 1; Err bitreich.org 70 i- S->S[PARALLELISM_DEGREE - 1]->last_node = 1; Err bitreich.org 70 i- { Err bitreich.org 70 i- uint8_t block[BLAKE2B_BLOCKBYTES]; Err bitreich.org 70 i- memset( block, 0, BLAKE2B_BLOCKBYTES ); Err bitreich.org 70 i- memcpy( block, key, keylen ); Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- blake2b_update( S->S[i], block, BLAKE2B_BLOCKBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- secure_zero_memory( block, BLAKE2B_BLOCKBYTES ); /* Burn the key from stack */ Err bitreich.org 70 i- } Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2bp_update( blake2bp_state *S, const void *pin, size_t inlen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- const unsigned char * in = (const unsigned char *)pin; Err bitreich.org 70 i- size_t left = S->buflen; Err bitreich.org 70 i- size_t fill = sizeof( S->buf ) - left; Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if( left && inlen >= fill ) Err bitreich.org 70 i- { Err bitreich.org 70 i- memcpy( S->buf + left, in, fill ); Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- blake2b_update( S->S[i], S->buf + i * BLAKE2B_BLOCKBYTES, BLAKE2B_BLOCKBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- in += fill; Err bitreich.org 70 i- inlen -= fill; Err bitreich.org 70 i- left = 0; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i-#if defined(_OPENMP) Err bitreich.org 70 i- #pragma omp parallel shared(S), num_threads(PARALLELISM_DEGREE) Err bitreich.org 70 i-#else Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i-#endif Err bitreich.org 70 i- { Err bitreich.org 70 i-#if defined(_OPENMP) Err bitreich.org 70 i- size_t i = omp_get_thread_num(); Err bitreich.org 70 i-#endif Err bitreich.org 70 i- size_t inlen__ = inlen; Err bitreich.org 70 i- const unsigned char *in__ = ( const unsigned char * )in; Err bitreich.org 70 i- in__ += i * BLAKE2B_BLOCKBYTES; Err bitreich.org 70 i- Err bitreich.org 70 i- while( inlen__ >= PARALLELISM_DEGREE * BLAKE2B_BLOCKBYTES ) Err bitreich.org 70 i- { Err bitreich.org 70 i- blake2b_update( S->S[i], in__, BLAKE2B_BLOCKBYTES ); Err bitreich.org 70 i- in__ += PARALLELISM_DEGREE * BLAKE2B_BLOCKBYTES; Err bitreich.org 70 i- inlen__ -= PARALLELISM_DEGREE * BLAKE2B_BLOCKBYTES; Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- in += inlen - inlen % ( PARALLELISM_DEGREE * BLAKE2B_BLOCKBYTES ); Err bitreich.org 70 i- inlen %= PARALLELISM_DEGREE * BLAKE2B_BLOCKBYTES; Err bitreich.org 70 i- Err bitreich.org 70 i- if( inlen > 0 ) Err bitreich.org 70 i- memcpy( S->buf + left, in, inlen ); Err bitreich.org 70 i- Err bitreich.org 70 i- S->buflen = left + inlen; Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2bp_final( blake2bp_state *S, void *out, size_t outlen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t hash[PARALLELISM_DEGREE][BLAKE2B_OUTBYTES]; Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if(out == NULL || outlen < S->outlen) { Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- { Err bitreich.org 70 i- if( S->buflen > i * BLAKE2B_BLOCKBYTES ) Err bitreich.org 70 i- { Err bitreich.org 70 i- size_t left = S->buflen - i * BLAKE2B_BLOCKBYTES; Err bitreich.org 70 i- Err bitreich.org 70 i- if( left > BLAKE2B_BLOCKBYTES ) left = BLAKE2B_BLOCKBYTES; Err bitreich.org 70 i- Err bitreich.org 70 i- blake2b_update( S->S[i], S->buf + i * BLAKE2B_BLOCKBYTES, left ); Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- blake2b_final( S->S[i], hash[i], BLAKE2B_OUTBYTES ); Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- blake2b_update( S->R, hash[i], BLAKE2B_OUTBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- return blake2b_final( S->R, out, S->outlen ); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2bp( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t hash[PARALLELISM_DEGREE][BLAKE2B_OUTBYTES]; Err bitreich.org 70 i- blake2b_state S[PARALLELISM_DEGREE][1]; Err bitreich.org 70 i- blake2b_state FS[1]; Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- /* Verify parameters */ Err bitreich.org 70 i- if ( NULL == in && inlen > 0 ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if ( NULL == out ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if( NULL == key && keylen > 0 ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if( !outlen || outlen > BLAKE2B_OUTBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if( keylen > BLAKE2B_KEYBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- if( blake2bp_init_leaf( S[i], outlen, keylen, i ) < 0 ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- S[PARALLELISM_DEGREE - 1]->last_node = 1; /* mark last node */ Err bitreich.org 70 i- Err bitreich.org 70 i- if( keylen > 0 ) Err bitreich.org 70 i- { Err bitreich.org 70 i- uint8_t block[BLAKE2B_BLOCKBYTES]; Err bitreich.org 70 i- memset( block, 0, BLAKE2B_BLOCKBYTES ); Err bitreich.org 70 i- memcpy( block, key, keylen ); Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- blake2b_update( S[i], block, BLAKE2B_BLOCKBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- secure_zero_memory( block, BLAKE2B_BLOCKBYTES ); /* Burn the key from stack */ Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i-#if defined(_OPENMP) Err bitreich.org 70 i- #pragma omp parallel shared(S,hash), num_threads(PARALLELISM_DEGREE) Err bitreich.org 70 i-#else Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i-#endif Err bitreich.org 70 i- { Err bitreich.org 70 i-#if defined(_OPENMP) Err bitreich.org 70 i- size_t i = omp_get_thread_num(); Err bitreich.org 70 i-#endif Err bitreich.org 70 i- size_t inlen__ = inlen; Err bitreich.org 70 i- const unsigned char *in__ = ( const unsigned char * )in; Err bitreich.org 70 i- in__ += i * BLAKE2B_BLOCKBYTES; Err bitreich.org 70 i- Err bitreich.org 70 i- while( inlen__ >= PARALLELISM_DEGREE * BLAKE2B_BLOCKBYTES ) Err bitreich.org 70 i- { Err bitreich.org 70 i- blake2b_update( S[i], in__, BLAKE2B_BLOCKBYTES ); Err bitreich.org 70 i- in__ += PARALLELISM_DEGREE * BLAKE2B_BLOCKBYTES; Err bitreich.org 70 i- inlen__ -= PARALLELISM_DEGREE * BLAKE2B_BLOCKBYTES; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- if( inlen__ > i * BLAKE2B_BLOCKBYTES ) Err bitreich.org 70 i- { Err bitreich.org 70 i- const size_t left = inlen__ - i * BLAKE2B_BLOCKBYTES; Err bitreich.org 70 i- const size_t len = left <= BLAKE2B_BLOCKBYTES ? left : BLAKE2B_BLOCKBYTES; Err bitreich.org 70 i- blake2b_update( S[i], in__, len ); Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- blake2b_final( S[i], hash[i], BLAKE2B_OUTBYTES ); Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- if( blake2bp_init_root( FS, outlen, keylen ) < 0 ) Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- FS->last_node = 1; /* Mark as last node */ Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- blake2b_update( FS, hash[i], BLAKE2B_OUTBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- return blake2b_final( FS, out, outlen );; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-#if defined(BLAKE2BP_SELFTEST) Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include "blake2-kat.h" Err bitreich.org 70 i-int main( void ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t key[BLAKE2B_KEYBYTES]; Err bitreich.org 70 i- uint8_t buf[BLAKE2_KAT_LENGTH]; Err bitreich.org 70 i- size_t i, step; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < BLAKE2B_KEYBYTES; ++i ) Err bitreich.org 70 i- key[i] = ( uint8_t )i; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < BLAKE2_KAT_LENGTH; ++i ) Err bitreich.org 70 i- buf[i] = ( uint8_t )i; Err bitreich.org 70 i- Err bitreich.org 70 i- /* Test simple API */ Err bitreich.org 70 i- for( i = 0; i < BLAKE2_KAT_LENGTH; ++i ) Err bitreich.org 70 i- { Err bitreich.org 70 i- uint8_t hash[BLAKE2B_OUTBYTES]; Err bitreich.org 70 i- blake2bp( hash, BLAKE2B_OUTBYTES, buf, i, key, BLAKE2B_KEYBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- if( 0 != memcmp( hash, blake2bp_keyed_kat[i], BLAKE2B_OUTBYTES ) ) Err bitreich.org 70 i- { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- /* Test streaming API */ Err bitreich.org 70 i- for(step = 1; step < BLAKE2B_BLOCKBYTES; ++step) { Err bitreich.org 70 i- for (i = 0; i < BLAKE2_KAT_LENGTH; ++i) { Err bitreich.org 70 i- uint8_t hash[BLAKE2B_OUTBYTES]; Err bitreich.org 70 i- blake2bp_state S; Err bitreich.org 70 i- uint8_t * p = buf; Err bitreich.org 70 i- size_t mlen = i; Err bitreich.org 70 i- int err = 0; Err bitreich.org 70 i- Err bitreich.org 70 i- if( (err = blake2bp_init_key(&S, BLAKE2B_OUTBYTES, key, BLAKE2B_KEYBYTES)) < 0 ) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- while (mlen >= step) { Err bitreich.org 70 i- if ( (err = blake2bp_update(&S, p, step)) < 0 ) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- mlen -= step; Err bitreich.org 70 i- p += step; Err bitreich.org 70 i- } Err bitreich.org 70 i- if ( (err = blake2bp_update(&S, p, mlen)) < 0) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- if ( (err = blake2bp_final(&S, hash, BLAKE2B_OUTBYTES)) < 0) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- if (0 != memcmp(hash, blake2bp_keyed_kat[i], BLAKE2B_OUTBYTES)) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- puts( "ok" ); Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-fail: Err bitreich.org 70 i- puts("error"); Err bitreich.org 70 i- return -1; Err bitreich.org 70 i-} Err bitreich.org 70 i-#endif Err bitreich.org 70 1diff --git a/blake2s-ref.c b/blake2s-ref.c /scm/dedup/file/blake2s-ref.c.gph bitreich.org 70 i@@ -1,367 +0,0 @@ Err bitreich.org 70 i-/* Err bitreich.org 70 i- BLAKE2 reference source code package - reference C implementations Err bitreich.org 70 i- Err bitreich.org 70 i- Copyright 2012, Samuel Neves . You may use this under the Err bitreich.org 70 i- terms of the CC0, the OpenSSL Licence, or the Apache Public License 2.0, at Err bitreich.org 70 i- your option. The terms of these licenses can be found at: Err bitreich.org 70 i- Err bitreich.org 70 i- - CC0 1.0 Universal : http://creativecommons.org/publicdomain/zero/1.0 Err bitreich.org 70 i- - OpenSSL license : https://www.openssl.org/source/license.html Err bitreich.org 70 i- - Apache 2.0 : http://www.apache.org/licenses/LICENSE-2.0 Err bitreich.org 70 i- Err bitreich.org 70 i- More information about the BLAKE2 hash function can be found at Err bitreich.org 70 i- https://blake2.net. Err bitreich.org 70 i-*/ Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "blake2-impl.h" Err bitreich.org 70 i- Err bitreich.org 70 i-static const uint32_t blake2s_IV[8] = Err bitreich.org 70 i-{ Err bitreich.org 70 i- 0x6A09E667UL, 0xBB67AE85UL, 0x3C6EF372UL, 0xA54FF53AUL, Err bitreich.org 70 i- 0x510E527FUL, 0x9B05688CUL, 0x1F83D9ABUL, 0x5BE0CD19UL Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-static const uint8_t blake2s_sigma[10][16] = Err bitreich.org 70 i-{ Err bitreich.org 70 i- { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 } , Err bitreich.org 70 i- { 14, 10, 4, 8, 9, 15, 13, 6, 1, 12, 0, 2, 11, 7, 5, 3 } , Err bitreich.org 70 i- { 11, 8, 12, 0, 5, 2, 15, 13, 10, 14, 3, 6, 7, 1, 9, 4 } , Err bitreich.org 70 i- { 7, 9, 3, 1, 13, 12, 11, 14, 2, 6, 5, 10, 4, 0, 15, 8 } , Err bitreich.org 70 i- { 9, 0, 5, 7, 2, 4, 10, 15, 14, 1, 11, 12, 6, 8, 3, 13 } , Err bitreich.org 70 i- { 2, 12, 6, 10, 0, 11, 8, 3, 4, 13, 7, 5, 15, 14, 1, 9 } , Err bitreich.org 70 i- { 12, 5, 1, 15, 14, 13, 4, 10, 0, 7, 6, 3, 9, 2, 8, 11 } , Err bitreich.org 70 i- { 13, 11, 7, 14, 12, 1, 3, 9, 5, 0, 15, 4, 8, 6, 2, 10 } , Err bitreich.org 70 i- { 6, 15, 14, 9, 11, 3, 0, 8, 12, 2, 13, 7, 1, 4, 10, 5 } , Err bitreich.org 70 i- { 10, 2, 8, 4, 7, 6, 1, 5, 15, 11, 9, 14, 3, 12, 13 , 0 } , Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-static void blake2s_set_lastnode( blake2s_state *S ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- S->f[1] = (uint32_t)-1; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-/* Some helper functions, not necessarily useful */ Err bitreich.org 70 i-static int blake2s_is_lastblock( const blake2s_state *S ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return S->f[0] != 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void blake2s_set_lastblock( blake2s_state *S ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- if( S->last_node ) blake2s_set_lastnode( S ); Err bitreich.org 70 i- Err bitreich.org 70 i- S->f[0] = (uint32_t)-1; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void blake2s_increment_counter( blake2s_state *S, const uint32_t inc ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- S->t[0] += inc; Err bitreich.org 70 i- S->t[1] += ( S->t[0] < inc ); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void blake2s_init0( blake2s_state *S ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- memset( S, 0, sizeof( blake2s_state ) ); Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < 8; ++i ) S->h[i] = blake2s_IV[i]; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-/* init2 xors IV with input parameter block */ Err bitreich.org 70 i-int blake2s_init_param( blake2s_state *S, const blake2s_param *P ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- const unsigned char *p = ( const unsigned char * )( P ); Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- blake2s_init0( S ); Err bitreich.org 70 i- Err bitreich.org 70 i- /* IV XOR ParamBlock */ Err bitreich.org 70 i- for( i = 0; i < 8; ++i ) Err bitreich.org 70 i- S->h[i] ^= load32( &p[i * 4] ); Err bitreich.org 70 i- Err bitreich.org 70 i- S->outlen = P->digest_length; Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i- Err bitreich.org 70 i-/* Sequential blake2s initialization */ Err bitreich.org 70 i-int blake2s_init( blake2s_state *S, size_t outlen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- blake2s_param P[1]; Err bitreich.org 70 i- Err bitreich.org 70 i- /* Move interval verification here? */ Err bitreich.org 70 i- if ( ( !outlen ) || ( outlen > BLAKE2S_OUTBYTES ) ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- P->digest_length = (uint8_t)outlen; Err bitreich.org 70 i- P->key_length = 0; Err bitreich.org 70 i- P->fanout = 1; Err bitreich.org 70 i- P->depth = 1; Err bitreich.org 70 i- store32( &P->leaf_length, 0 ); Err bitreich.org 70 i- store32( &P->node_offset, 0 ); Err bitreich.org 70 i- store16( &P->xof_length, 0 ); Err bitreich.org 70 i- P->node_depth = 0; Err bitreich.org 70 i- P->inner_length = 0; Err bitreich.org 70 i- /* memset(P->reserved, 0, sizeof(P->reserved) ); */ Err bitreich.org 70 i- memset( P->salt, 0, sizeof( P->salt ) ); Err bitreich.org 70 i- memset( P->personal, 0, sizeof( P->personal ) ); Err bitreich.org 70 i- return blake2s_init_param( S, P ); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2s_init_key( blake2s_state *S, size_t outlen, const void *key, size_t keylen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- blake2s_param P[1]; Err bitreich.org 70 i- Err bitreich.org 70 i- if ( ( !outlen ) || ( outlen > BLAKE2S_OUTBYTES ) ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if ( !key || !keylen || keylen > BLAKE2S_KEYBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- P->digest_length = (uint8_t)outlen; Err bitreich.org 70 i- P->key_length = (uint8_t)keylen; Err bitreich.org 70 i- P->fanout = 1; Err bitreich.org 70 i- P->depth = 1; Err bitreich.org 70 i- store32( &P->leaf_length, 0 ); Err bitreich.org 70 i- store32( &P->node_offset, 0 ); Err bitreich.org 70 i- store16( &P->xof_length, 0 ); Err bitreich.org 70 i- P->node_depth = 0; Err bitreich.org 70 i- P->inner_length = 0; Err bitreich.org 70 i- /* memset(P->reserved, 0, sizeof(P->reserved) ); */ Err bitreich.org 70 i- memset( P->salt, 0, sizeof( P->salt ) ); Err bitreich.org 70 i- memset( P->personal, 0, sizeof( P->personal ) ); Err bitreich.org 70 i- Err bitreich.org 70 i- if( blake2s_init_param( S, P ) < 0 ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- { Err bitreich.org 70 i- uint8_t block[BLAKE2S_BLOCKBYTES]; Err bitreich.org 70 i- memset( block, 0, BLAKE2S_BLOCKBYTES ); Err bitreich.org 70 i- memcpy( block, key, keylen ); Err bitreich.org 70 i- blake2s_update( S, block, BLAKE2S_BLOCKBYTES ); Err bitreich.org 70 i- secure_zero_memory( block, BLAKE2S_BLOCKBYTES ); /* Burn the key from stack */ Err bitreich.org 70 i- } Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-#define G(r,i,a,b,c,d) \ Err bitreich.org 70 i- do { \ Err bitreich.org 70 i- a = a + b + m[blake2s_sigma[r][2*i+0]]; \ Err bitreich.org 70 i- d = rotr32(d ^ a, 16); \ Err bitreich.org 70 i- c = c + d; \ Err bitreich.org 70 i- b = rotr32(b ^ c, 12); \ Err bitreich.org 70 i- a = a + b + m[blake2s_sigma[r][2*i+1]]; \ Err bitreich.org 70 i- d = rotr32(d ^ a, 8); \ Err bitreich.org 70 i- c = c + d; \ Err bitreich.org 70 i- b = rotr32(b ^ c, 7); \ Err bitreich.org 70 i- } while(0) Err bitreich.org 70 i- Err bitreich.org 70 i-#define ROUND(r) \ Err bitreich.org 70 i- do { \ Err bitreich.org 70 i- G(r,0,v[ 0],v[ 4],v[ 8],v[12]); \ Err bitreich.org 70 i- G(r,1,v[ 1],v[ 5],v[ 9],v[13]); \ Err bitreich.org 70 i- G(r,2,v[ 2],v[ 6],v[10],v[14]); \ Err bitreich.org 70 i- G(r,3,v[ 3],v[ 7],v[11],v[15]); \ Err bitreich.org 70 i- G(r,4,v[ 0],v[ 5],v[10],v[15]); \ Err bitreich.org 70 i- G(r,5,v[ 1],v[ 6],v[11],v[12]); \ Err bitreich.org 70 i- G(r,6,v[ 2],v[ 7],v[ 8],v[13]); \ Err bitreich.org 70 i- G(r,7,v[ 3],v[ 4],v[ 9],v[14]); \ Err bitreich.org 70 i- } while(0) Err bitreich.org 70 i- Err bitreich.org 70 i-static void blake2s_compress( blake2s_state *S, const uint8_t in[BLAKE2S_BLOCKBYTES] ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint32_t m[16]; Err bitreich.org 70 i- uint32_t v[16]; Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < 16; ++i ) { Err bitreich.org 70 i- m[i] = load32( in + i * sizeof( m[i] ) ); Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < 8; ++i ) { Err bitreich.org 70 i- v[i] = S->h[i]; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- v[ 8] = blake2s_IV[0]; Err bitreich.org 70 i- v[ 9] = blake2s_IV[1]; Err bitreich.org 70 i- v[10] = blake2s_IV[2]; Err bitreich.org 70 i- v[11] = blake2s_IV[3]; Err bitreich.org 70 i- v[12] = S->t[0] ^ blake2s_IV[4]; Err bitreich.org 70 i- v[13] = S->t[1] ^ blake2s_IV[5]; Err bitreich.org 70 i- v[14] = S->f[0] ^ blake2s_IV[6]; Err bitreich.org 70 i- v[15] = S->f[1] ^ blake2s_IV[7]; Err bitreich.org 70 i- Err bitreich.org 70 i- ROUND( 0 ); Err bitreich.org 70 i- ROUND( 1 ); Err bitreich.org 70 i- ROUND( 2 ); Err bitreich.org 70 i- ROUND( 3 ); Err bitreich.org 70 i- ROUND( 4 ); Err bitreich.org 70 i- ROUND( 5 ); Err bitreich.org 70 i- ROUND( 6 ); Err bitreich.org 70 i- ROUND( 7 ); Err bitreich.org 70 i- ROUND( 8 ); Err bitreich.org 70 i- ROUND( 9 ); Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < 8; ++i ) { Err bitreich.org 70 i- S->h[i] = S->h[i] ^ v[i] ^ v[i + 8]; Err bitreich.org 70 i- } Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-#undef G Err bitreich.org 70 i-#undef ROUND Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2s_update( blake2s_state *S, const void *pin, size_t inlen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- const unsigned char * in = (const unsigned char *)pin; Err bitreich.org 70 i- if( inlen > 0 ) Err bitreich.org 70 i- { Err bitreich.org 70 i- size_t left = S->buflen; Err bitreich.org 70 i- size_t fill = BLAKE2S_BLOCKBYTES - left; Err bitreich.org 70 i- if( inlen > fill ) Err bitreich.org 70 i- { Err bitreich.org 70 i- S->buflen = 0; Err bitreich.org 70 i- memcpy( S->buf + left, in, fill ); /* Fill buffer */ Err bitreich.org 70 i- blake2s_increment_counter( S, BLAKE2S_BLOCKBYTES ); Err bitreich.org 70 i- blake2s_compress( S, S->buf ); /* Compress */ Err bitreich.org 70 i- in += fill; inlen -= fill; Err bitreich.org 70 i- while(inlen > BLAKE2S_BLOCKBYTES) { Err bitreich.org 70 i- blake2s_increment_counter(S, BLAKE2S_BLOCKBYTES); Err bitreich.org 70 i- blake2s_compress( S, in ); Err bitreich.org 70 i- in += BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- inlen -= BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- memcpy( S->buf + S->buflen, in, inlen ); Err bitreich.org 70 i- S->buflen += inlen; Err bitreich.org 70 i- } Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2s_final( blake2s_state *S, void *out, size_t outlen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t buffer[BLAKE2S_OUTBYTES] = {0}; Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if( out == NULL || outlen < S->outlen ) Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if( blake2s_is_lastblock( S ) ) Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- blake2s_increment_counter( S, ( uint32_t )S->buflen ); Err bitreich.org 70 i- blake2s_set_lastblock( S ); Err bitreich.org 70 i- memset( S->buf + S->buflen, 0, BLAKE2S_BLOCKBYTES - S->buflen ); /* Padding */ Err bitreich.org 70 i- blake2s_compress( S, S->buf ); Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < 8; ++i ) /* Output full hash to temp buffer */ Err bitreich.org 70 i- store32( buffer + sizeof( S->h[i] ) * i, S->h[i] ); Err bitreich.org 70 i- Err bitreich.org 70 i- memcpy( out, buffer, outlen ); Err bitreich.org 70 i- secure_zero_memory(buffer, sizeof(buffer)); Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2s( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- blake2s_state S[1]; Err bitreich.org 70 i- Err bitreich.org 70 i- /* Verify parameters */ Err bitreich.org 70 i- if ( NULL == in && inlen > 0 ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if ( NULL == out ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if ( NULL == key && keylen > 0) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if( !outlen || outlen > BLAKE2S_OUTBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if( keylen > BLAKE2S_KEYBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if( keylen > 0 ) Err bitreich.org 70 i- { Err bitreich.org 70 i- if( blake2s_init_key( S, outlen, key, keylen ) < 0 ) return -1; Err bitreich.org 70 i- } Err bitreich.org 70 i- else Err bitreich.org 70 i- { Err bitreich.org 70 i- if( blake2s_init( S, outlen ) < 0 ) return -1; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- blake2s_update( S, ( const uint8_t * )in, inlen ); Err bitreich.org 70 i- blake2s_final( S, out, outlen ); Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-#if defined(SUPERCOP) Err bitreich.org 70 i-int crypto_hash( unsigned char *out, unsigned char *in, unsigned long long inlen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2s( out, BLAKE2S_OUTBYTES, in, inlen, NULL, 0 ); Err bitreich.org 70 i-} Err bitreich.org 70 i-#endif Err bitreich.org 70 i- Err bitreich.org 70 i-#if defined(BLAKE2S_SELFTEST) Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include "blake2-kat.h" Err bitreich.org 70 i-int main( void ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t key[BLAKE2S_KEYBYTES]; Err bitreich.org 70 i- uint8_t buf[BLAKE2_KAT_LENGTH]; Err bitreich.org 70 i- size_t i, step; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < BLAKE2S_KEYBYTES; ++i ) Err bitreich.org 70 i- key[i] = ( uint8_t )i; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < BLAKE2_KAT_LENGTH; ++i ) Err bitreich.org 70 i- buf[i] = ( uint8_t )i; Err bitreich.org 70 i- Err bitreich.org 70 i- /* Test simple API */ Err bitreich.org 70 i- for( i = 0; i < BLAKE2_KAT_LENGTH; ++i ) Err bitreich.org 70 i- { Err bitreich.org 70 i- uint8_t hash[BLAKE2S_OUTBYTES]; Err bitreich.org 70 i- blake2s( hash, BLAKE2S_OUTBYTES, buf, i, key, BLAKE2S_KEYBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- if( 0 != memcmp( hash, blake2s_keyed_kat[i], BLAKE2S_OUTBYTES ) ) Err bitreich.org 70 i- { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- /* Test streaming API */ Err bitreich.org 70 i- for(step = 1; step < BLAKE2S_BLOCKBYTES; ++step) { Err bitreich.org 70 i- for (i = 0; i < BLAKE2_KAT_LENGTH; ++i) { Err bitreich.org 70 i- uint8_t hash[BLAKE2S_OUTBYTES]; Err bitreich.org 70 i- blake2s_state S; Err bitreich.org 70 i- uint8_t * p = buf; Err bitreich.org 70 i- size_t mlen = i; Err bitreich.org 70 i- int err = 0; Err bitreich.org 70 i- Err bitreich.org 70 i- if( (err = blake2s_init_key(&S, BLAKE2S_OUTBYTES, key, BLAKE2S_KEYBYTES)) < 0 ) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- while (mlen >= step) { Err bitreich.org 70 i- if ( (err = blake2s_update(&S, p, step)) < 0 ) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- mlen -= step; Err bitreich.org 70 i- p += step; Err bitreich.org 70 i- } Err bitreich.org 70 i- if ( (err = blake2s_update(&S, p, mlen)) < 0) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- if ( (err = blake2s_final(&S, hash, BLAKE2S_OUTBYTES)) < 0) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- if (0 != memcmp(hash, blake2s_keyed_kat[i], BLAKE2S_OUTBYTES)) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- puts( "ok" ); Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-fail: Err bitreich.org 70 i- puts("error"); Err bitreich.org 70 i- return -1; Err bitreich.org 70 i-} Err bitreich.org 70 i-#endif Err bitreich.org 70 1diff --git a/blake2sp-ref.c b/blake2sp-ref.c /scm/dedup/file/blake2sp-ref.c.gph bitreich.org 70 i@@ -1,359 +0,0 @@ Err bitreich.org 70 i-/* Err bitreich.org 70 i- BLAKE2 reference source code package - reference C implementations Err bitreich.org 70 i- Err bitreich.org 70 i- Copyright 2012, Samuel Neves . You may use this under the Err bitreich.org 70 i- terms of the CC0, the OpenSSL Licence, or the Apache Public License 2.0, at Err bitreich.org 70 i- your option. The terms of these licenses can be found at: Err bitreich.org 70 i- Err bitreich.org 70 i- - CC0 1.0 Universal : http://creativecommons.org/publicdomain/zero/1.0 Err bitreich.org 70 i- - OpenSSL license : https://www.openssl.org/source/license.html Err bitreich.org 70 i- - Apache 2.0 : http://www.apache.org/licenses/LICENSE-2.0 Err bitreich.org 70 i- Err bitreich.org 70 i- More information about the BLAKE2 hash function can be found at Err bitreich.org 70 i- https://blake2.net. Err bitreich.org 70 i-*/ Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#if defined(_OPENMP) Err bitreich.org 70 i-#include Err bitreich.org 70 i-#endif Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "blake2-impl.h" Err bitreich.org 70 i- Err bitreich.org 70 i-#define PARALLELISM_DEGREE 8 Err bitreich.org 70 i- Err bitreich.org 70 i-/* Err bitreich.org 70 i- blake2sp_init_param defaults to setting the expecting output length Err bitreich.org 70 i- from the digest_length parameter block field. Err bitreich.org 70 i- Err bitreich.org 70 i- In some cases, however, we do not want this, as the output length Err bitreich.org 70 i- of these instances is given by inner_length instead. Err bitreich.org 70 i-*/ Err bitreich.org 70 i-static int blake2sp_init_leaf_param( blake2s_state *S, const blake2s_param *P ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- int err = blake2s_init_param(S, P); Err bitreich.org 70 i- S->outlen = P->inner_length; Err bitreich.org 70 i- return err; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static int blake2sp_init_leaf( blake2s_state *S, size_t outlen, size_t keylen, uint64_t offset ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- blake2s_param P[1]; Err bitreich.org 70 i- P->digest_length = (uint8_t)outlen; Err bitreich.org 70 i- P->key_length = (uint8_t)keylen; Err bitreich.org 70 i- P->fanout = PARALLELISM_DEGREE; Err bitreich.org 70 i- P->depth = 2; Err bitreich.org 70 i- store32( &P->leaf_length, 0 ); Err bitreich.org 70 i- store32( &P->node_offset, offset ); Err bitreich.org 70 i- store16( &P->xof_length, 0 ); Err bitreich.org 70 i- P->node_depth = 0; Err bitreich.org 70 i- P->inner_length = BLAKE2S_OUTBYTES; Err bitreich.org 70 i- memset( P->salt, 0, sizeof( P->salt ) ); Err bitreich.org 70 i- memset( P->personal, 0, sizeof( P->personal ) ); Err bitreich.org 70 i- return blake2sp_init_leaf_param( S, P ); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static int blake2sp_init_root( blake2s_state *S, size_t outlen, size_t keylen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- blake2s_param P[1]; Err bitreich.org 70 i- P->digest_length = (uint8_t)outlen; Err bitreich.org 70 i- P->key_length = (uint8_t)keylen; Err bitreich.org 70 i- P->fanout = PARALLELISM_DEGREE; Err bitreich.org 70 i- P->depth = 2; Err bitreich.org 70 i- store32( &P->leaf_length, 0 ); Err bitreich.org 70 i- store32( &P->node_offset, 0 ); Err bitreich.org 70 i- store16( &P->xof_length, 0 ); Err bitreich.org 70 i- P->node_depth = 1; Err bitreich.org 70 i- P->inner_length = BLAKE2S_OUTBYTES; Err bitreich.org 70 i- memset( P->salt, 0, sizeof( P->salt ) ); Err bitreich.org 70 i- memset( P->personal, 0, sizeof( P->personal ) ); Err bitreich.org 70 i- return blake2s_init_param( S, P ); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2sp_init( blake2sp_state *S, size_t outlen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if( !outlen || outlen > BLAKE2S_OUTBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- memset( S->buf, 0, sizeof( S->buf ) ); Err bitreich.org 70 i- S->buflen = 0; Err bitreich.org 70 i- S->outlen = outlen; Err bitreich.org 70 i- Err bitreich.org 70 i- if( blake2sp_init_root( S->R, outlen, 0 ) < 0 ) Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- if( blake2sp_init_leaf( S->S[i], outlen, 0, i ) < 0 ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- S->R->last_node = 1; Err bitreich.org 70 i- S->S[PARALLELISM_DEGREE - 1]->last_node = 1; Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2sp_init_key( blake2sp_state *S, size_t outlen, const void *key, size_t keylen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if( !outlen || outlen > BLAKE2S_OUTBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if( !key || !keylen || keylen > BLAKE2S_KEYBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- memset( S->buf, 0, sizeof( S->buf ) ); Err bitreich.org 70 i- S->buflen = 0; Err bitreich.org 70 i- S->outlen = outlen; Err bitreich.org 70 i- Err bitreich.org 70 i- if( blake2sp_init_root( S->R, outlen, keylen ) < 0 ) Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- if( blake2sp_init_leaf( S->S[i], outlen, keylen, i ) < 0 ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- S->R->last_node = 1; Err bitreich.org 70 i- S->S[PARALLELISM_DEGREE - 1]->last_node = 1; Err bitreich.org 70 i- { Err bitreich.org 70 i- uint8_t block[BLAKE2S_BLOCKBYTES]; Err bitreich.org 70 i- memset( block, 0, BLAKE2S_BLOCKBYTES ); Err bitreich.org 70 i- memcpy( block, key, keylen ); Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- blake2s_update( S->S[i], block, BLAKE2S_BLOCKBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- secure_zero_memory( block, BLAKE2S_BLOCKBYTES ); /* Burn the key from stack */ Err bitreich.org 70 i- } Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2sp_update( blake2sp_state *S, const void *pin, size_t inlen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- const unsigned char * in = (const unsigned char *)pin; Err bitreich.org 70 i- size_t left = S->buflen; Err bitreich.org 70 i- size_t fill = sizeof( S->buf ) - left; Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if( left && inlen >= fill ) Err bitreich.org 70 i- { Err bitreich.org 70 i- memcpy( S->buf + left, in, fill ); Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- blake2s_update( S->S[i], S->buf + i * BLAKE2S_BLOCKBYTES, BLAKE2S_BLOCKBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- in += fill; Err bitreich.org 70 i- inlen -= fill; Err bitreich.org 70 i- left = 0; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i-#if defined(_OPENMP) Err bitreich.org 70 i- #pragma omp parallel shared(S), num_threads(PARALLELISM_DEGREE) Err bitreich.org 70 i-#else Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i-#endif Err bitreich.org 70 i- { Err bitreich.org 70 i-#if defined(_OPENMP) Err bitreich.org 70 i- size_t i = omp_get_thread_num(); Err bitreich.org 70 i-#endif Err bitreich.org 70 i- size_t inlen__ = inlen; Err bitreich.org 70 i- const unsigned char *in__ = ( const unsigned char * )in; Err bitreich.org 70 i- in__ += i * BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- Err bitreich.org 70 i- while( inlen__ >= PARALLELISM_DEGREE * BLAKE2S_BLOCKBYTES ) Err bitreich.org 70 i- { Err bitreich.org 70 i- blake2s_update( S->S[i], in__, BLAKE2S_BLOCKBYTES ); Err bitreich.org 70 i- in__ += PARALLELISM_DEGREE * BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- inlen__ -= PARALLELISM_DEGREE * BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- in += inlen - inlen % ( PARALLELISM_DEGREE * BLAKE2S_BLOCKBYTES ); Err bitreich.org 70 i- inlen %= PARALLELISM_DEGREE * BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- Err bitreich.org 70 i- if( inlen > 0 ) Err bitreich.org 70 i- memcpy( S->buf + left, in, inlen ); Err bitreich.org 70 i- Err bitreich.org 70 i- S->buflen = left + inlen; Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2sp_final( blake2sp_state *S, void *out, size_t outlen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t hash[PARALLELISM_DEGREE][BLAKE2S_OUTBYTES]; Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if(out == NULL || outlen < S->outlen) { Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- { Err bitreich.org 70 i- if( S->buflen > i * BLAKE2S_BLOCKBYTES ) Err bitreich.org 70 i- { Err bitreich.org 70 i- size_t left = S->buflen - i * BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- Err bitreich.org 70 i- if( left > BLAKE2S_BLOCKBYTES ) left = BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- Err bitreich.org 70 i- blake2s_update( S->S[i], S->buf + i * BLAKE2S_BLOCKBYTES, left ); Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- blake2s_final( S->S[i], hash[i], BLAKE2S_OUTBYTES ); Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- blake2s_update( S->R, hash[i], BLAKE2S_OUTBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- return blake2s_final( S->R, out, S->outlen ); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i- Err bitreich.org 70 i-int blake2sp( void *out, size_t outlen, const void *in, size_t inlen, const void *key, size_t keylen ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t hash[PARALLELISM_DEGREE][BLAKE2S_OUTBYTES]; Err bitreich.org 70 i- blake2s_state S[PARALLELISM_DEGREE][1]; Err bitreich.org 70 i- blake2s_state FS[1]; Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- /* Verify parameters */ Err bitreich.org 70 i- if ( NULL == in && inlen > 0 ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if ( NULL == out ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if ( NULL == key && keylen > 0) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if( !outlen || outlen > BLAKE2S_OUTBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- if( keylen > BLAKE2S_KEYBYTES ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- if( blake2sp_init_leaf( S[i], outlen, keylen, i ) < 0 ) return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- S[PARALLELISM_DEGREE - 1]->last_node = 1; /* mark last node */ Err bitreich.org 70 i- Err bitreich.org 70 i- if( keylen > 0 ) Err bitreich.org 70 i- { Err bitreich.org 70 i- uint8_t block[BLAKE2S_BLOCKBYTES]; Err bitreich.org 70 i- memset( block, 0, BLAKE2S_BLOCKBYTES ); Err bitreich.org 70 i- memcpy( block, key, keylen ); Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- blake2s_update( S[i], block, BLAKE2S_BLOCKBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- secure_zero_memory( block, BLAKE2S_BLOCKBYTES ); /* Burn the key from stack */ Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i-#if defined(_OPENMP) Err bitreich.org 70 i- #pragma omp parallel shared(S,hash), num_threads(PARALLELISM_DEGREE) Err bitreich.org 70 i-#else Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i-#endif Err bitreich.org 70 i- { Err bitreich.org 70 i-#if defined(_OPENMP) Err bitreich.org 70 i- size_t i = omp_get_thread_num(); Err bitreich.org 70 i-#endif Err bitreich.org 70 i- size_t inlen__ = inlen; Err bitreich.org 70 i- const unsigned char *in__ = ( const unsigned char * )in; Err bitreich.org 70 i- in__ += i * BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- Err bitreich.org 70 i- while( inlen__ >= PARALLELISM_DEGREE * BLAKE2S_BLOCKBYTES ) Err bitreich.org 70 i- { Err bitreich.org 70 i- blake2s_update( S[i], in__, BLAKE2S_BLOCKBYTES ); Err bitreich.org 70 i- in__ += PARALLELISM_DEGREE * BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- inlen__ -= PARALLELISM_DEGREE * BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- if( inlen__ > i * BLAKE2S_BLOCKBYTES ) Err bitreich.org 70 i- { Err bitreich.org 70 i- const size_t left = inlen__ - i * BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- const size_t len = left <= BLAKE2S_BLOCKBYTES ? left : BLAKE2S_BLOCKBYTES; Err bitreich.org 70 i- blake2s_update( S[i], in__, len ); Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- blake2s_final( S[i], hash[i], BLAKE2S_OUTBYTES ); Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- if( blake2sp_init_root( FS, outlen, keylen ) < 0 ) Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- FS->last_node = 1; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < PARALLELISM_DEGREE; ++i ) Err bitreich.org 70 i- blake2s_update( FS, hash[i], BLAKE2S_OUTBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- return blake2s_final( FS, out, outlen ); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i- Err bitreich.org 70 i- Err bitreich.org 70 i-#if defined(BLAKE2SP_SELFTEST) Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include "blake2-kat.h" Err bitreich.org 70 i-int main( void ) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t key[BLAKE2S_KEYBYTES]; Err bitreich.org 70 i- uint8_t buf[BLAKE2_KAT_LENGTH]; Err bitreich.org 70 i- size_t i, step; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < BLAKE2S_KEYBYTES; ++i ) Err bitreich.org 70 i- key[i] = ( uint8_t )i; Err bitreich.org 70 i- Err bitreich.org 70 i- for( i = 0; i < BLAKE2_KAT_LENGTH; ++i ) Err bitreich.org 70 i- buf[i] = ( uint8_t )i; Err bitreich.org 70 i- Err bitreich.org 70 i- /* Test simple API */ Err bitreich.org 70 i- for( i = 0; i < BLAKE2_KAT_LENGTH; ++i ) Err bitreich.org 70 i- { Err bitreich.org 70 i- uint8_t hash[BLAKE2S_OUTBYTES]; Err bitreich.org 70 i- blake2sp( hash, BLAKE2S_OUTBYTES, buf, i, key, BLAKE2S_KEYBYTES ); Err bitreich.org 70 i- Err bitreich.org 70 i- if( 0 != memcmp( hash, blake2sp_keyed_kat[i], BLAKE2S_OUTBYTES ) ) Err bitreich.org 70 i- { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- /* Test streaming API */ Err bitreich.org 70 i- for(step = 1; step < BLAKE2S_BLOCKBYTES; ++step) { Err bitreich.org 70 i- for (i = 0; i < BLAKE2_KAT_LENGTH; ++i) { Err bitreich.org 70 i- uint8_t hash[BLAKE2S_OUTBYTES]; Err bitreich.org 70 i- blake2sp_state S; Err bitreich.org 70 i- uint8_t * p = buf; Err bitreich.org 70 i- size_t mlen = i; Err bitreich.org 70 i- int err = 0; Err bitreich.org 70 i- Err bitreich.org 70 i- if( (err = blake2sp_init_key(&S, BLAKE2S_OUTBYTES, key, BLAKE2S_KEYBYTES)) < 0 ) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- while (mlen >= step) { Err bitreich.org 70 i- if ( (err = blake2sp_update(&S, p, step)) < 0 ) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- mlen -= step; Err bitreich.org 70 i- p += step; Err bitreich.org 70 i- } Err bitreich.org 70 i- if ( (err = blake2sp_update(&S, p, mlen)) < 0) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- if ( (err = blake2sp_final(&S, hash, BLAKE2S_OUTBYTES)) < 0) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- if (0 != memcmp(hash, blake2sp_keyed_kat[i], BLAKE2S_OUTBYTES)) { Err bitreich.org 70 i- goto fail; Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- puts( "ok" ); Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-fail: Err bitreich.org 70 i- puts("error"); Err bitreich.org 70 i- return -1; Err bitreich.org 70 i-} Err bitreich.org 70 i-#endif Err bitreich.org 70 1diff --git a/block.c b/block.c /scm/dedup/file/block.c.gph bitreich.org 70 i@@ -0,0 +1,114 @@ Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+ Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+ Err bitreich.org 70 i+#include "block.h" Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+bcreat(char *path, int mode, struct bparam *bpar, struct bctx **bctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct bops *bops; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (path == NULL || bctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (bpar == NULL) Err bitreich.org 70 i+ bpar = bparamdef(); Err bitreich.org 70 i+ Err bitreich.org 70 i+ *bctx = calloc(1, sizeof(**bctx)); Err bitreich.org 70 i+ if (*bctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bops = bcompressops(); Err bitreich.org 70 i+ if (bops->creat(*bctx, path, mode, bpar) < 0) { Err bitreich.org 70 i+ free(*bctx); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+bopen(char *path, int flags, int mode, struct bparam *bpar, struct bctx **bctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct bops *bops; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (path == NULL || bpar == NULL || bctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ *bctx = calloc(1, sizeof(**bctx)); Err bitreich.org 70 i+ if (*bctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bops = bcompressops(); Err bitreich.org 70 i+ if (bops->open(*bctx, path, flags, mode, bpar) < 0) { Err bitreich.org 70 i+ free(*bctx); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+bput(struct bctx *bctx, void *buf, size_t n, unsigned char *md) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct bops *bops; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (bctx == NULL || buf == NULL || n == 0 || md == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bops = bcompressops(); Err bitreich.org 70 i+ return bops->put(bctx, buf, n, md); Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+bget(struct bctx *bctx, unsigned char *md, void *buf, size_t *n) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct bops *bops; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (bctx == NULL || md == NULL || buf == NULL || n == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bops = bcompressops(); Err bitreich.org 70 i+ return bops->get(bctx, md, buf, n); Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+bsync(struct bctx *bctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct bops *bops; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (bctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bops = bcompressops(); Err bitreich.org 70 i+ return bops->sync(bctx); Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+bclose(struct bctx *bctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct bops *bops; Err bitreich.org 70 i+ int r; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (bctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (bsync(bctx) < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ bops = bcompressops(); Err bitreich.org 70 i+ r = bops->close(bctx); Err bitreich.org 70 i+ free(bctx); Err bitreich.org 70 i+ return r; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+struct bparam * Err bitreich.org 70 i+bparamdef(void) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ static struct bparam bpar = { .calgo = "snappy", .halgo = "blake2b" }; Err bitreich.org 70 i+ Err bitreich.org 70 i+ return &bpar; Err bitreich.org 70 i+} Err bitreich.org 70 1diff --git a/block.h b/block.h /scm/dedup/file/block.h.gph bitreich.org 70 i@@ -0,0 +1,34 @@ Err bitreich.org 70 i+struct bctx { Err bitreich.org 70 i+ void *rctx; /* raw layer context */ Err bitreich.org 70 i+ void *cctx; /* compression layer context */ Err bitreich.org 70 i+ void *sctx; /* storage layer context */ Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+struct bparam { Err bitreich.org 70 i+ char *calgo; Err bitreich.org 70 i+ char *halgo; Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+struct bops { Err bitreich.org 70 i+ int (*creat)(struct bctx *bctx, char *path, int mode, struct bparam *bpar); Err bitreich.org 70 i+ int (*open)(struct bctx *bctx, char *path, int flags, int mode, struct bparam *bpar); Err bitreich.org 70 i+ int (*put)(struct bctx *bctx, void *buf, size_t n, unsigned char *md); Err bitreich.org 70 i+ int (*get)(struct bctx *bctx, unsigned char *md, void *buf, size_t *n); Err bitreich.org 70 i+ int (*sync)(struct bctx *bctx); Err bitreich.org 70 i+ int (*close)(struct bctx *bctx); Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+/* block.c */ Err bitreich.org 70 i+extern int bcreat(char *path, int mode, struct bparam *bpar, struct bctx **bctx); Err bitreich.org 70 i+extern int bopen(char *path, int flags, int mode, struct bparam *bpar, struct bctx **bctx); Err bitreich.org 70 i+extern int bput(struct bctx *bctx, void *buf, size_t n, unsigned char *md); Err bitreich.org 70 i+extern int bget(struct bctx *bctx, unsigned char *md, void *buf, size_t *n); Err bitreich.org 70 i+extern int bsync(struct bctx *bctx); Err bitreich.org 70 i+extern int bclose(struct bctx *bctx); Err bitreich.org 70 i+struct bparam *bparamdef(void); Err bitreich.org 70 i+ Err bitreich.org 70 i+/* bcompress.c */ Err bitreich.org 70 i+extern struct bops *bcompressops(void); Err bitreich.org 70 i+ Err bitreich.org 70 i+/* bstorage.c */ Err bitreich.org 70 i+extern struct bops *bstorageops(void); Err bitreich.org 70 1diff --git a/bstorage.c b/bstorage.c /scm/dedup/file/bstorage.c.gph bitreich.org 70 i@@ -0,0 +1,564 @@ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * Storage layer implementation using a single backing file. Err bitreich.org 70 i+ * The file format is as follows: Err bitreich.org 70 i+ * Err bitreich.org 70 i+ * [storage header] Err bitreich.org 70 i+ * [storage descriptor 0] Err bitreich.org 70 i+ * [data] Err bitreich.org 70 i+ * [storage descriptor 1] Err bitreich.org 70 i+ * [data] Err bitreich.org 70 i+ * ... Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+ Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+ Err bitreich.org 70 i+#include "blake2.h" Err bitreich.org 70 i+#include "block.h" Err bitreich.org 70 i+#include "config.h" Err bitreich.org 70 i+#include "tree.h" Err bitreich.org 70 i+ Err bitreich.org 70 i+#define VMIN 0 Err bitreich.org 70 i+#define VMAJ 1 Err bitreich.org 70 i+ Err bitreich.org 70 i+#define VMINMASK 0xff Err bitreich.org 70 i+#define VMAJSHIFT 8 Err bitreich.org 70 i+#define VMAJMASK 0xff Err bitreich.org 70 i+ Err bitreich.org 70 i+#define HALGOSHIFT 19 Err bitreich.org 70 i+#define HALGOMASK 0x7 Err bitreich.org 70 i+#define CALGOSHIFT 16 Err bitreich.org 70 i+#define CALGOMASK 0x7 Err bitreich.org 70 i+ Err bitreich.org 70 i+#define BHDRSIZE 16 Err bitreich.org 70 i+ Err bitreich.org 70 i+#define BDTYPE 0x100 Err bitreich.org 70 i+#define BDSIZE (8 + 8 + 8 + (MDSIZE)) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define CSNAPPYTYPE 0 Err bitreich.org 70 i+#define HBLAKE2BTYPE 0 Err bitreich.org 70 i+ Err bitreich.org 70 i+extern int pack(unsigned char *dst, char *fmt, ...); Err bitreich.org 70 i+extern int unpack(unsigned char *src, char *fmt, ...); Err bitreich.org 70 i+ Err bitreich.org 70 i+static int bscreat(struct bctx *bctx, char *path, int mode, struct bparam *bpar); Err bitreich.org 70 i+static int bsopen(struct bctx *bctx, char *path, int flags, int mode, struct bparam *bpar); Err bitreich.org 70 i+static int bsput(struct bctx *bctx, void *buf, size_t n, unsigned char *md); Err bitreich.org 70 i+static int bsget(struct bctx *bctx, unsigned char *md, void *buf, size_t *n); Err bitreich.org 70 i+static int bssync(struct bctx *bctx); Err bitreich.org 70 i+static int bsclose(struct bctx *bctx); Err bitreich.org 70 i+ Err bitreich.org 70 i+static struct bops bops = { Err bitreich.org 70 i+ .creat = bscreat, Err bitreich.org 70 i+ .open = bsopen, Err bitreich.org 70 i+ .put = bsput, Err bitreich.org 70 i+ .get = bsget, Err bitreich.org 70 i+ .sync = bssync, Err bitreich.org 70 i+ .close = bsclose, Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Block header structure */ Err bitreich.org 70 i+struct bhdr { Err bitreich.org 70 i+ uint64_t flags; Err bitreich.org 70 i+ uint64_t nent; Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Block descriptor */ Err bitreich.org 70 i+struct bd { Err bitreich.org 70 i+ uint64_t type; Err bitreich.org 70 i+ uint64_t offset; Err bitreich.org 70 i+ uint64_t size; Err bitreich.org 70 i+ unsigned char md[MDSIZE]; Err bitreich.org 70 i+ RB_ENTRY(bd) entry; Err bitreich.org 70 i+}; Err bitreich.org 70 i+RB_HEAD(bdcache, bd); Err bitreich.org 70 i+ Err bitreich.org 70 i+struct sctx { Err bitreich.org 70 i+ struct bdcache bdcache; Err bitreich.org 70 i+ struct bhdr bhdr; Err bitreich.org 70 i+ int fd; Err bitreich.org 70 i+ int rdonly; Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+static char *ctbl[] = { Err bitreich.org 70 i+ "snappy", Err bitreich.org 70 i+ NULL, Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+static char *htbl[] = { Err bitreich.org 70 i+ "blake2b", Err bitreich.org 70 i+ NULL, Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bd_cmp(struct bd *b1, struct bd *b2) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ int r; Err bitreich.org 70 i+ Err bitreich.org 70 i+ r = memcmp(b1->md, b2->md, MDSIZE); Err bitreich.org 70 i+ if (r > 0) Err bitreich.org 70 i+ return 1; Err bitreich.org 70 i+ else if (r < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+static RB_PROTOTYPE(bdcache, bd, entry, bd_cmp) Err bitreich.org 70 i+static RB_GENERATE(bdcache, bd, entry, bd_cmp) Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bhash(void *buf, size_t n, unsigned char *md) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ blake2b_state ctx; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (blake2b_init(&ctx, MDSIZE) < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ if (blake2b_update(&ctx, buf, n) < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ return blake2b_final(&ctx, md, MDSIZE); Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static ssize_t Err bitreich.org 70 i+xread(int fd, void *buf, size_t nbytes) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ unsigned char *bp = buf; Err bitreich.org 70 i+ ssize_t total = 0; Err bitreich.org 70 i+ Err bitreich.org 70 i+ while (nbytes > 0) { Err bitreich.org 70 i+ ssize_t n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ n = read(fd, &bp[total], nbytes); Err bitreich.org 70 i+ if (n < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ else if (n == 0) Err bitreich.org 70 i+ return total; Err bitreich.org 70 i+ total += n; Err bitreich.org 70 i+ nbytes -= n; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return total; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static ssize_t Err bitreich.org 70 i+xwrite(int fd, void *buf, size_t nbytes) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ unsigned char *bp = buf; Err bitreich.org 70 i+ ssize_t total = 0; Err bitreich.org 70 i+ Err bitreich.org 70 i+ while (nbytes > 0) { Err bitreich.org 70 i+ ssize_t n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ n = write(fd, &bp[total], nbytes); Err bitreich.org 70 i+ if (n < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ else if (n == 0) Err bitreich.org 70 i+ return total; Err bitreich.org 70 i+ total += n; Err bitreich.org 70 i+ nbytes -= n; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return total; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Read block header */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+unpackbhdr(int fd, struct bhdr *bhdr) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ unsigned char buf[BHDRSIZE]; Err bitreich.org 70 i+ int n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (xread(fd, buf, sizeof(buf)) != sizeof(buf)) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ n = unpack(buf, "qq", Err bitreich.org 70 i+ &bhdr->flags, Err bitreich.org 70 i+ &bhdr->nent); Err bitreich.org 70 i+ Err bitreich.org 70 i+ assert(n == sizeof(buf)); Err bitreich.org 70 i+ return n; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Write block header */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+packbhdr(int fd, struct bhdr *bhdr) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ unsigned char buf[BHDRSIZE]; Err bitreich.org 70 i+ int n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ n = pack(buf, "qq", Err bitreich.org 70 i+ bhdr->flags, Err bitreich.org 70 i+ bhdr->nent); Err bitreich.org 70 i+ Err bitreich.org 70 i+ assert(n == BHDRSIZE); Err bitreich.org 70 i+ if (xwrite(fd, buf, n) != n) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ return n; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Read block descriptor */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+unpackbd(int fd, struct bd *bd) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ unsigned char buf[BDSIZE]; Err bitreich.org 70 i+ char fmt[BUFSIZ]; Err bitreich.org 70 i+ int n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (xread(fd, buf, sizeof(buf)) != sizeof(buf)) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ snprintf(fmt, sizeof(fmt), "qqq'%d", MDSIZE); Err bitreich.org 70 i+ n = unpack(buf, fmt, Err bitreich.org 70 i+ &bd->type, Err bitreich.org 70 i+ &bd->offset, Err bitreich.org 70 i+ &bd->size, Err bitreich.org 70 i+ bd->md); Err bitreich.org 70 i+ Err bitreich.org 70 i+ assert(n == BDSIZE); Err bitreich.org 70 i+ return n; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Write block descriptor */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+packbd(int fd, struct bd *bd) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ unsigned char buf[BDSIZE]; Err bitreich.org 70 i+ char fmt[BUFSIZ]; Err bitreich.org 70 i+ int n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ snprintf(fmt, sizeof(fmt), "qqq'%d", MDSIZE); Err bitreich.org 70 i+ n = pack(buf, fmt, Err bitreich.org 70 i+ bd->type, Err bitreich.org 70 i+ bd->offset, Err bitreich.org 70 i+ bd->size, Err bitreich.org 70 i+ bd->md); Err bitreich.org 70 i+ Err bitreich.org 70 i+ assert(n == BDSIZE); Err bitreich.org 70 i+ if (xwrite(fd, buf, n) != n) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ return n; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Insert block descriptor to cache */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+loadbd(struct sctx *sctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct bd *bd; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bd = calloc(1, sizeof(*bd)); Err bitreich.org 70 i+ if (bd == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (unpackbd(sctx->fd, bd) < 0) { Err bitreich.org 70 i+ free(bd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (bd->type != BDTYPE) { Err bitreich.org 70 i+ free(bd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ /* Move to the next block descriptor */ Err bitreich.org 70 i+ if (lseek(sctx->fd, bd->size, SEEK_CUR) < 0) { Err bitreich.org 70 i+ free(bd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ RB_INSERT(bdcache, &sctx->bdcache, bd); Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Initialize block descriptor cache */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+initbdcache(struct sctx *sctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct bhdr *bhdr; Err bitreich.org 70 i+ uint64_t i; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bhdr = &sctx->bhdr; Err bitreich.org 70 i+ for (i = 0; i < bhdr->nent; i++) { Err bitreich.org 70 i+ struct bd *bd, *tmp; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (loadbd(sctx) == 0) Err bitreich.org 70 i+ continue; Err bitreich.org 70 i+ Err bitreich.org 70 i+ /* Cleanup */ Err bitreich.org 70 i+ RB_FOREACH_SAFE(bd, bdcache, &sctx->bdcache, tmp) { Err bitreich.org 70 i+ RB_REMOVE(bdcache, &sctx->bdcache, bd); Err bitreich.org 70 i+ free(bd); Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Create a new store */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bscreat(struct bctx *bctx, char *path, int mode, struct bparam *bpar) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct sctx *sctx; Err bitreich.org 70 i+ struct bhdr *bhdr; Err bitreich.org 70 i+ char **algo; Err bitreich.org 70 i+ int fd; Err bitreich.org 70 i+ Err bitreich.org 70 i+ fd = open(path, O_RDWR | O_CREAT | O_EXCL, mode); Err bitreich.org 70 i+ if (fd < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bctx->sctx = calloc(1, sizeof(struct sctx)); Err bitreich.org 70 i+ if (bctx->sctx == NULL) { Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ sctx = bctx->sctx; Err bitreich.org 70 i+ RB_INIT(&sctx->bdcache); Err bitreich.org 70 i+ bhdr = &sctx->bhdr; Err bitreich.org 70 i+ bhdr->flags = (VMAJ << VMAJSHIFT) | VMIN; Err bitreich.org 70 i+ Err bitreich.org 70 i+ /* Set compression algorithm */ Err bitreich.org 70 i+ for (algo = ctbl; algo; algo++) { Err bitreich.org 70 i+ if (strcmp(*algo, bpar->calgo) == 0) { Err bitreich.org 70 i+ uint64_t v; Err bitreich.org 70 i+ Err bitreich.org 70 i+ v = algo - ctbl; Err bitreich.org 70 i+ bhdr->flags |= v << CALGOSHIFT; Err bitreich.org 70 i+ break; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ } Err bitreich.org 70 i+ if (algo == NULL) { Err bitreich.org 70 i+ free(sctx); Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ /* Set hash algorithm */ Err bitreich.org 70 i+ for (algo = htbl; algo; algo++) { Err bitreich.org 70 i+ if (strcmp(*algo, bpar->halgo) == 0) { Err bitreich.org 70 i+ uint64_t v; Err bitreich.org 70 i+ Err bitreich.org 70 i+ v = algo - htbl; Err bitreich.org 70 i+ bhdr->flags |= v << HALGOSHIFT; Err bitreich.org 70 i+ break; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ } Err bitreich.org 70 i+ if (algo == NULL) { Err bitreich.org 70 i+ free(sctx); Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ bhdr->nent = 0; Err bitreich.org 70 i+ sctx->fd = fd; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (packbhdr(fd, bhdr) < 0) { Err bitreich.org 70 i+ free(sctx); Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Open an existing store */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bsopen(struct bctx *bctx, char *path, int flags, int mode, struct bparam *bpar) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct sctx *sctx; Err bitreich.org 70 i+ struct bhdr *bhdr; Err bitreich.org 70 i+ char **algo; Err bitreich.org 70 i+ int fd, calgo, halgo; Err bitreich.org 70 i+ Err bitreich.org 70 i+ fd = open(path, flags, mode); Err bitreich.org 70 i+ if (fd < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bctx->sctx = calloc(1, sizeof(struct sctx)); Err bitreich.org 70 i+ if (bctx->sctx == NULL) { Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ sctx = bctx->sctx; Err bitreich.org 70 i+ RB_INIT(&sctx->bdcache); Err bitreich.org 70 i+ bhdr = &sctx->bhdr; Err bitreich.org 70 i+ if (unpackbhdr(fd, bhdr) < 0) { Err bitreich.org 70 i+ free(sctx); Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ /* If the major version is different, the format is incompatible */ Err bitreich.org 70 i+ if (((bhdr->flags >> VMAJSHIFT) & VMAJMASK) != VMAJ) { Err bitreich.org 70 i+ free(sctx); Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ /* Get compression algorithm */ Err bitreich.org 70 i+ calgo = (bhdr->flags >> CALGOSHIFT) & CALGOMASK; Err bitreich.org 70 i+ for (algo = ctbl; algo; algo++) { Err bitreich.org 70 i+ uint64_t v = algo - ctbl; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (v == calgo) { Err bitreich.org 70 i+ bpar->calgo = ctbl[v]; Err bitreich.org 70 i+ break; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ } Err bitreich.org 70 i+ if (algo == NULL) { Err bitreich.org 70 i+ free(sctx); Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ /* Get hash algorithm */ Err bitreich.org 70 i+ halgo = (bhdr->flags >> CALGOSHIFT) & CALGOMASK; Err bitreich.org 70 i+ for (algo = htbl; algo; algo++) { Err bitreich.org 70 i+ uint64_t v = algo - htbl; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (v == halgo) { Err bitreich.org 70 i+ bpar->halgo = htbl[v]; Err bitreich.org 70 i+ break; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ } Err bitreich.org 70 i+ if (algo == NULL) { Err bitreich.org 70 i+ free(sctx); Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ sctx->fd = fd; Err bitreich.org 70 i+ sctx->rdonly = flags == O_RDONLY; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (initbdcache(sctx) < 0) { Err bitreich.org 70 i+ free(sctx); Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Write a new block */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bsput(struct bctx *bctx, void *buf, size_t n, unsigned char *md) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct sctx *sctx; Err bitreich.org 70 i+ struct bhdr *bhdr; Err bitreich.org 70 i+ struct bd key, *bd; Err bitreich.org 70 i+ off_t offs; Err bitreich.org 70 i+ Err bitreich.org 70 i+ sctx = bctx->sctx; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (bhash(buf, n, key.md) < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bd = RB_FIND(bdcache, &sctx->bdcache, &key); Err bitreich.org 70 i+ if (bd != NULL) { Err bitreich.org 70 i+ memcpy(md, bd->md, MDSIZE); Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ offs = lseek(sctx->fd, 0, SEEK_END); Err bitreich.org 70 i+ if (offs < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ bd = calloc(1, sizeof(*bd)); Err bitreich.org 70 i+ if (bd == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ bd->type = BDTYPE; Err bitreich.org 70 i+ bd->offset = offs + BDSIZE; Err bitreich.org 70 i+ bd->size = n; Err bitreich.org 70 i+ memcpy(bd->md, key.md, MDSIZE); Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (packbd(sctx->fd, bd) < 0) { Err bitreich.org 70 i+ free(bd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (xwrite(sctx->fd, buf, n) != n) { Err bitreich.org 70 i+ ftruncate(sctx->fd, offs); Err bitreich.org 70 i+ free(bd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ bhdr = &sctx->bhdr; Err bitreich.org 70 i+ bhdr->nent++; Err bitreich.org 70 i+ RB_INSERT(bdcache, &sctx->bdcache, bd); Err bitreich.org 70 i+ memcpy(md, bd->md, MDSIZE); Err bitreich.org 70 i+ return bd->size; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Read a block */ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bsget(struct bctx *bctx, unsigned char *md, void *buf, size_t *n) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct sctx *sctx; Err bitreich.org 70 i+ struct bd key, *bd; Err bitreich.org 70 i+ Err bitreich.org 70 i+ sctx = bctx->sctx; Err bitreich.org 70 i+ Err bitreich.org 70 i+ /* Lookup block in the cache */ Err bitreich.org 70 i+ memcpy(key.md, md, MDSIZE); Err bitreich.org 70 i+ bd = RB_FIND(bdcache, &sctx->bdcache, &key); Err bitreich.org 70 i+ if (bd == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (*n < bd->size) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (lseek(sctx->fd, bd->offset, SEEK_SET) < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ if (xread(sctx->fd, buf, bd->size) != bd->size) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ *n = bd->size; Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bssync(struct bctx *bctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct sctx *sctx; Err bitreich.org 70 i+ struct bhdr *bhdr; Err bitreich.org 70 i+ Err bitreich.org 70 i+ sctx = bctx->sctx; Err bitreich.org 70 i+ if (sctx->rdonly) Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (lseek(sctx->fd, 0, SEEK_SET) < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ bhdr = &sctx->bhdr; Err bitreich.org 70 i+ if (packbhdr(sctx->fd, bhdr) < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ fsync(sctx->fd); Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+bsclose(struct bctx *bctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct sctx *sctx; Err bitreich.org 70 i+ struct bd *bd, *tmp; Err bitreich.org 70 i+ int r; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (bssync(bctx) < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ sctx = bctx->sctx; Err bitreich.org 70 i+ RB_FOREACH_SAFE(bd, bdcache, &sctx->bdcache, tmp) { Err bitreich.org 70 i+ RB_REMOVE(bdcache, &sctx->bdcache, bd); Err bitreich.org 70 i+ free(bd); Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ r = close(sctx->fd); Err bitreich.org 70 i+ free(sctx); Err bitreich.org 70 i+ return r; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+struct bops * Err bitreich.org 70 i+bstorageops(void) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ return &bops; Err bitreich.org 70 i+} Err bitreich.org 70 1diff --git a/chunker.c b/chunker.c /scm/dedup/file/chunker.c.gph bitreich.org 70 i@@ -1,24 +1,20 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i #include Err bitreich.org 70 i #include Err bitreich.org 70 i #include Err bitreich.org 70 i #include Err bitreich.org 70 i #include Err bitreich.org 70 i Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i #define ROTL(x, y) (((x) << (y)) | ((x) >> (32 - (y)))) Err bitreich.org 70 i Err bitreich.org 70 i struct chunker { Err bitreich.org 70 i- uint8_t *buf; Err bitreich.org 70 i+ unsigned char *buf; Err bitreich.org 70 i int fd; Err bitreich.org 70 i- size_t rpos; Err bitreich.org 70 i- size_t wpos; Err bitreich.org 70 i- size_t min_size; Err bitreich.org 70 i- size_t max_size; Err bitreich.org 70 i+ size_t rp; Err bitreich.org 70 i+ size_t wp; Err bitreich.org 70 i+ size_t minsize; Err bitreich.org 70 i+ size_t maxsize; Err bitreich.org 70 i size_t mask; Err bitreich.org 70 i- size_t win_size; Err bitreich.org 70 i+ size_t winsize; Err bitreich.org 70 i }; Err bitreich.org 70 i Err bitreich.org 70 i /* Err bitreich.org 70 i@@ -30,7 +26,7 @@ struct chunker { Err bitreich.org 70 i * exactly 50% chance that a XOR operation would flip all the bits in Err bitreich.org 70 i * the hash. Err bitreich.org 70 i */ Err bitreich.org 70 i-static const uint32_t buz[] = { Err bitreich.org 70 i+static const uint32_t buztbl[] = { Err bitreich.org 70 i 0xbc9fa594,0x30a8f827,0xced627a7,0xdb46a745,0xcfa4a9e8,0x77cccb59,0xddb66276,0x3adc532f, Err bitreich.org 70 i 0xfe8b67d3,0x8155b59e,0x0c893666,0x1d757009,0x17394ee4,0x85d94c07,0xcacd52da,0x076c6f79, Err bitreich.org 70 i 0xead0a798,0x6c7ccb4a,0x2639a1b8,0x3aa5ae32,0x3e6218d2,0xb290d980,0xa5149521,0x4b426119, Err bitreich.org 70 i@@ -65,36 +61,55 @@ static const uint32_t buz[] = { Err bitreich.org 70 i 0x8dfd4d53,0xc4d0c087,0x31dfb5ca,0xa44589b5,0x6b637e2e,0x663f6b45,0xd2d8baa0,0x1dac7e4c Err bitreich.org 70 i }; Err bitreich.org 70 i Err bitreich.org 70 i+static ssize_t Err bitreich.org 70 i+xread(int fd, void *buf, size_t nbytes) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ unsigned char *bp = buf; Err bitreich.org 70 i+ ssize_t total = 0; Err bitreich.org 70 i+ Err bitreich.org 70 i+ while (nbytes > 0) { Err bitreich.org 70 i+ ssize_t n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ n = read(fd, &bp[total], nbytes); Err bitreich.org 70 i+ if (n < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ else if (n == 0) Err bitreich.org 70 i+ return total; Err bitreich.org 70 i+ total += n; Err bitreich.org 70 i+ nbytes -= n; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return total; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i /* Buzhash: https://en.wikipedia.org/wiki/Rolling_hash#Cyclic_polynomial */ Err bitreich.org 70 i static inline uint32_t Err bitreich.org 70 i-buzh_init(uint8_t *buf, size_t size) Err bitreich.org 70 i+hinit(unsigned char *buf, size_t size) Err bitreich.org 70 i { Err bitreich.org 70 i uint32_t sum; Err bitreich.org 70 i size_t i; Err bitreich.org 70 i Err bitreich.org 70 i for (i = 1, sum = 0; i < size; i++, buf++) Err bitreich.org 70 i- sum ^= ROTL(buz[*buf], (size - i) % 32); Err bitreich.org 70 i- Err bitreich.org 70 i- return sum ^ buz[*buf]; Err bitreich.org 70 i+ sum ^= ROTL(buztbl[*buf], (size - i) % 32); Err bitreich.org 70 i+ return sum ^ buztbl[*buf]; Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i static inline uint32_t Err bitreich.org 70 i-buzh_update(uint32_t sum, uint8_t out, uint8_t in, size_t size) Err bitreich.org 70 i+hupdate(uint32_t sum, unsigned char out, unsigned char in, size_t size) Err bitreich.org 70 i { Err bitreich.org 70 i- return ROTL(sum, 1) ^ ROTL(buz[out], size % 32) ^ buz[in]; Err bitreich.org 70 i+ return ROTL(sum, 1) ^ ROTL(buztbl[out], size % 32) ^ buztbl[in]; Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i static size_t Err bitreich.org 70 i-get_chunk_size(struct chunker *chunker) Err bitreich.org 70 i+cgetsize(struct chunker *c) Err bitreich.org 70 i { Err bitreich.org 70 i- size_t max_chunk_size, win_size, i; Err bitreich.org 70 i+ size_t maxcsize, winsize, i; Err bitreich.org 70 i uint32_t sum; Err bitreich.org 70 i- uint8_t *bp; Err bitreich.org 70 i+ unsigned char *bp; Err bitreich.org 70 i Err bitreich.org 70 i- max_chunk_size = chunker->wpos - chunker->rpos; Err bitreich.org 70 i- win_size = chunker->win_size; Err bitreich.org 70 i- if (max_chunk_size < win_size) Err bitreich.org 70 i- return max_chunk_size; Err bitreich.org 70 i+ maxcsize = c->wp - c->rp; Err bitreich.org 70 i+ winsize = c->winsize; Err bitreich.org 70 i+ if (maxcsize < winsize) Err bitreich.org 70 i+ return maxcsize; Err bitreich.org 70 i Err bitreich.org 70 i /* Err bitreich.org 70 i * To achieve better deduplication, we chunk blocks based on a Err bitreich.org 70 i@@ -104,93 +119,96 @@ get_chunk_size(struct chunker *chunker) Err bitreich.org 70 i * When the rolling hash matches a given pattern the block is chunked Err bitreich.org 70 i * at the end of that window. Err bitreich.org 70 i */ Err bitreich.org 70 i- bp = &chunker->buf[chunker->rpos]; Err bitreich.org 70 i- sum = buzh_init(bp, win_size); Err bitreich.org 70 i- for (i = 0; i < max_chunk_size - win_size; i++) { Err bitreich.org 70 i- size_t chunk_size = i + win_size; Err bitreich.org 70 i+ bp = &c->buf[c->rp]; Err bitreich.org 70 i+ sum = hinit(bp, winsize); Err bitreich.org 70 i+ for (i = 0; i < maxcsize - winsize; i++) { Err bitreich.org 70 i+ size_t csize = i + winsize; Err bitreich.org 70 i Err bitreich.org 70 i if (i > 0) { Err bitreich.org 70 i- uint8_t out = bp[i - 1]; Err bitreich.org 70 i- uint8_t in = bp[chunk_size - 1]; Err bitreich.org 70 i+ unsigned char out = bp[i - 1]; Err bitreich.org 70 i+ unsigned char in = bp[csize - 1]; Err bitreich.org 70 i Err bitreich.org 70 i- sum = buzh_update(sum, out, in, win_size); Err bitreich.org 70 i+ sum = hupdate(sum, out, in, winsize); Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i- if (chunk_size < chunker->min_size) Err bitreich.org 70 i+ if (csize < c->minsize) Err bitreich.org 70 i continue; Err bitreich.org 70 i Err bitreich.org 70 i- if ((sum & chunker->mask) == 0) Err bitreich.org 70 i- return chunk_size; Err bitreich.org 70 i+ if ((sum & c->mask) == 0) Err bitreich.org 70 i+ return csize; Err bitreich.org 70 i } Err bitreich.org 70 i- return max_chunk_size; Err bitreich.org 70 i+ return maxcsize; Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i struct chunker * Err bitreich.org 70 i-alloc_chunker(int fd, size_t min_size, size_t max_size, Err bitreich.org 70 i- size_t mask, size_t win_size) Err bitreich.org 70 i+copen(int fd, size_t minsize, size_t maxsize, Err bitreich.org 70 i+ size_t mask, size_t winsize) Err bitreich.org 70 i { Err bitreich.org 70 i- struct chunker *chunker; Err bitreich.org 70 i+ struct chunker *c; Err bitreich.org 70 i Err bitreich.org 70 i- chunker = calloc(1, sizeof(*chunker)); Err bitreich.org 70 i- if (chunker == NULL) Err bitreich.org 70 i- err(1, "calloc"); Err bitreich.org 70 i- Err bitreich.org 70 i- chunker->buf = calloc(1, max_size); Err bitreich.org 70 i- if (chunker->buf == NULL) Err bitreich.org 70 i- err(1, "calloc"); Err bitreich.org 70 i+ c = calloc(1, sizeof(*c)); Err bitreich.org 70 i+ if (c == NULL) Err bitreich.org 70 i+ return NULL; Err bitreich.org 70 i Err bitreich.org 70 i- chunker->fd = fd; Err bitreich.org 70 i- chunker->min_size = min_size; Err bitreich.org 70 i- chunker->max_size = max_size; Err bitreich.org 70 i- chunker->mask = mask; Err bitreich.org 70 i- chunker->win_size = win_size; Err bitreich.org 70 i+ c->buf = calloc(1, maxsize); Err bitreich.org 70 i+ if (c->buf == NULL) { Err bitreich.org 70 i+ free(c); Err bitreich.org 70 i+ return NULL; Err bitreich.org 70 i+ } Err bitreich.org 70 i Err bitreich.org 70 i- return chunker; Err bitreich.org 70 i+ c->fd = fd; Err bitreich.org 70 i+ c->minsize = minsize; Err bitreich.org 70 i+ c->maxsize = maxsize; Err bitreich.org 70 i+ c->mask = mask; Err bitreich.org 70 i+ c->winsize = winsize; Err bitreich.org 70 i+ return c; Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i-void Err bitreich.org 70 i-free_chunker(struct chunker *chunker) Err bitreich.org 70 i+int Err bitreich.org 70 i+cclose(struct chunker *c) Err bitreich.org 70 i { Err bitreich.org 70 i- free(chunker->buf); Err bitreich.org 70 i- free(chunker); Err bitreich.org 70 i+ free(c->buf); Err bitreich.org 70 i+ free(c); Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i ssize_t Err bitreich.org 70 i-fill_chunker(struct chunker *chunker) Err bitreich.org 70 i+cfill(struct chunker *c) Err bitreich.org 70 i { Err bitreich.org 70 i- uint8_t *bp; Err bitreich.org 70 i+ unsigned char *bp; Err bitreich.org 70 i ssize_t n; Err bitreich.org 70 i Err bitreich.org 70 i- bp = &chunker->buf[chunker->wpos]; Err bitreich.org 70 i- n = xread(chunker->fd, bp, chunker->max_size - chunker->wpos); Err bitreich.org 70 i- chunker->wpos += n; Err bitreich.org 70 i- return chunker->wpos; Err bitreich.org 70 i+ bp = &c->buf[c->wp]; Err bitreich.org 70 i+ n = xread(c->fd, bp, c->maxsize - c->wp); Err bitreich.org 70 i+ c->wp += n; Err bitreich.org 70 i+ return c->wp; Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i-uint8_t * Err bitreich.org 70 i-get_chunk(struct chunker *chunker, size_t *chunk_size) Err bitreich.org 70 i+void * Err bitreich.org 70 i+cget(struct chunker *c, size_t *csize) Err bitreich.org 70 i { Err bitreich.org 70 i- uint8_t *bp; Err bitreich.org 70 i+ unsigned char *bp; Err bitreich.org 70 i Err bitreich.org 70 i- if (chunker->rpos == chunker->wpos) { Err bitreich.org 70 i- *chunk_size = 0; Err bitreich.org 70 i+ if (c->rp == c->wp) { Err bitreich.org 70 i+ *csize = 0; Err bitreich.org 70 i return NULL; Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i- bp = &chunker->buf[chunker->rpos]; Err bitreich.org 70 i- *chunk_size = get_chunk_size(chunker); Err bitreich.org 70 i- chunker->rpos += *chunk_size; Err bitreich.org 70 i+ bp = &c->buf[c->rp]; Err bitreich.org 70 i+ *csize = cgetsize(c); Err bitreich.org 70 i+ c->rp += *csize; Err bitreich.org 70 i return bp; Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i-void Err bitreich.org 70 i-drain_chunker(struct chunker *chunker) Err bitreich.org 70 i+int Err bitreich.org 70 i+cdrain(struct chunker *c) Err bitreich.org 70 i { Err bitreich.org 70 i- uint8_t *src, *dst; Err bitreich.org 70 i- Err bitreich.org 70 i- src = &chunker->buf[chunker->rpos]; Err bitreich.org 70 i- dst = chunker->buf; Err bitreich.org 70 i- memmove(dst, src, chunker->wpos - chunker->rpos); Err bitreich.org 70 i- chunker->wpos -= chunker->rpos; Err bitreich.org 70 i- chunker->rpos = 0; Err bitreich.org 70 i+ unsigned char *src, *dst; Err bitreich.org 70 i+ Err bitreich.org 70 i+ src = &c->buf[c->rp]; Err bitreich.org 70 i+ dst = c->buf; Err bitreich.org 70 i+ memmove(dst, src, c->wp - c->rp); Err bitreich.org 70 i+ c->wp -= c->rp; Err bitreich.org 70 i+ c->rp = 0; Err bitreich.org 70 i+ return c->wp; Err bitreich.org 70 i } Err bitreich.org 70 1diff --git a/chunker.h b/chunker.h /scm/dedup/file/chunker.h.gph bitreich.org 70 i@@ -0,0 +1,8 @@ Err bitreich.org 70 i+struct chunker; Err bitreich.org 70 i+ Err bitreich.org 70 i+extern struct chunker *copen(int fd, size_t minsize, size_t maxsize, Err bitreich.org 70 i+ size_t mask, size_t winsize); Err bitreich.org 70 i+extern int cclose(struct chunker *c); Err bitreich.org 70 i+extern ssize_t cfill(struct chunker *c); Err bitreich.org 70 i+extern void *cget(struct chunker *c, size_t *csize); Err bitreich.org 70 i+extern int cdrain(struct chunker *c); Err bitreich.org 70 1diff --git a/compress-lz4.c b/compress-lz4.c /scm/dedup/file/compress-lz4.c.gph bitreich.org 70 i@@ -1,54 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-lz4_init(struct compr_ctx *ctx) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-size_t Err bitreich.org 70 i-lz4_size(struct compr_ctx *ctx, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return LZ4_compressBound(n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-size_t Err bitreich.org 70 i-lz4_compr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize) Err bitreich.org 70 i-{ Err bitreich.org 70 i- int n; Err bitreich.org 70 i- Err bitreich.org 70 i- n = LZ4_compress_default((char *)in, (char *)out, insize, Err bitreich.org 70 i- outsize); Err bitreich.org 70 i- if (n < 0) Err bitreich.org 70 i- errx(1, "LZ4_compress_default failed"); Err bitreich.org 70 i- return n; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-size_t Err bitreich.org 70 i-lz4_decompr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize) Err bitreich.org 70 i-{ Err bitreich.org 70 i- int n; Err bitreich.org 70 i- Err bitreich.org 70 i- n = LZ4_decompress_safe((char *)in, (char *)out, insize, Err bitreich.org 70 i- outsize); Err bitreich.org 70 i- if (n < 0) Err bitreich.org 70 i- errx(1, "LZ4_decompress_safe failed"); Err bitreich.org 70 i- return n; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-lz4_final(struct compr_ctx *ctx) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/compress-none.c b/compress-none.c /scm/dedup/file/compress-none.c.gph bitreich.org 70 i@@ -1,41 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-none_init(struct compr_ctx *ctx) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-size_t Err bitreich.org 70 i-none_size(struct compr_ctx *ctx, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return n; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-size_t Err bitreich.org 70 i-none_compr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize) Err bitreich.org 70 i-{ Err bitreich.org 70 i- memcpy(out, in, insize); Err bitreich.org 70 i- return insize; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-size_t Err bitreich.org 70 i-none_decompr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize) Err bitreich.org 70 i-{ Err bitreich.org 70 i- memcpy(out, in, insize); Err bitreich.org 70 i- return insize; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-none_final(struct compr_ctx *ctx) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/compress-snappy.c b/compress-snappy.c /scm/dedup/file/compress-snappy.c.gph bitreich.org 70 i@@ -1,54 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-snappy_init(struct compr_ctx *ctx) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-size_t Err bitreich.org 70 i-snappy_size(struct compr_ctx *ctx, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return snappy_max_compressed_length(n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-size_t Err bitreich.org 70 i-snappy_compr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t n = outsize; Err bitreich.org 70 i- snappy_status ret; Err bitreich.org 70 i- Err bitreich.org 70 i- ret = snappy_compress((char *)in, insize, (char *)out, &n); Err bitreich.org 70 i- if (ret != SNAPPY_OK) Err bitreich.org 70 i- errx(1, "snappy_compress failed: %d", ret); Err bitreich.org 70 i- return n; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-size_t Err bitreich.org 70 i-snappy_decompr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t n = outsize; Err bitreich.org 70 i- snappy_status ret; Err bitreich.org 70 i- Err bitreich.org 70 i- ret = snappy_uncompress((char *)in, insize, (char *)out, &n); Err bitreich.org 70 i- if (ret != SNAPPY_OK) Err bitreich.org 70 i- errx(1, "snappy_uncompress failed: %d", ret); Err bitreich.org 70 i- return n; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-snappy_final(struct compr_ctx *ctx) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/compress.c b/compress.c /scm/dedup/file/compress.c.gph bitreich.org 70 i@@ -1,112 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-static struct compr_ops { Err bitreich.org 70 i- int (*init)(struct compr_ctx *ctx); Err bitreich.org 70 i- size_t (*size)(struct compr_ctx *ctx, size_t n); Err bitreich.org 70 i- size_t (*compr)(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize); Err bitreich.org 70 i- size_t (*decompr)(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize); Err bitreich.org 70 i- int (*final)(struct compr_ctx *ctx); Err bitreich.org 70 i-} comprs[NR_COMPRS] = { Err bitreich.org 70 i- { Err bitreich.org 70 i- .init = none_init, Err bitreich.org 70 i- .size = none_size, Err bitreich.org 70 i- .compr = none_compr, Err bitreich.org 70 i- .decompr = none_decompr, Err bitreich.org 70 i- .final = none_final, Err bitreich.org 70 i- }, Err bitreich.org 70 i- { Err bitreich.org 70 i- .init = lz4_init, Err bitreich.org 70 i- .size = lz4_size, Err bitreich.org 70 i- .compr = lz4_compr, Err bitreich.org 70 i- .decompr = lz4_decompr, Err bitreich.org 70 i- .final = lz4_final, Err bitreich.org 70 i- }, Err bitreich.org 70 i- { Err bitreich.org 70 i- .init = snappy_init, Err bitreich.org 70 i- .size = snappy_size, Err bitreich.org 70 i- .compr = snappy_compr, Err bitreich.org 70 i- .decompr = snappy_decompr, Err bitreich.org 70 i- .final = snappy_final, Err bitreich.org 70 i- }, Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-static char *algomap[NR_COMPRS] = { Err bitreich.org 70 i- [COMPR_NONE] = "none", Err bitreich.org 70 i- [COMPR_LZ4] = "lz4", Err bitreich.org 70 i- [COMPR_SNAPPY] = "snappy", Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-compr_init(struct compr_ctx *ctx, int type) Err bitreich.org 70 i-{ Err bitreich.org 70 i- if (type < 0 || type >= NR_COMPRS) Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- ctx->ops = &comprs[type]; Err bitreich.org 70 i- return (*ctx->ops->init)(ctx); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-compr_size(struct compr_ctx *ctx, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return (*ctx->ops->size)(ctx, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-size_t Err bitreich.org 70 i-compr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return (*ctx->ops->compr)(ctx, in, out, insize, outsize); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-size_t Err bitreich.org 70 i-decompr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return (*ctx->ops->decompr)(ctx, in, out, insize, outsize); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-compr_final(struct compr_ctx *ctx) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return (*ctx->ops->final)(ctx); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-compr_name2type(char *name) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- for (i = 0; i < NR_COMPRS; i++) Err bitreich.org 70 i- if (strcasecmp(algomap[i], name) == 0) Err bitreich.org 70 i- return i; Err bitreich.org 70 i- return -1; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-char * Err bitreich.org 70 i-compr_type2name(int type) Err bitreich.org 70 i-{ Err bitreich.org 70 i- if (type < 0 || type >= NR_HASHES) Err bitreich.org 70 i- return NULL; Err bitreich.org 70 i- return algomap[type]; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-compr_list(int fd) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- for (i = 0; i < NR_COMPRS; i++) Err bitreich.org 70 i- dprintf(fd, "%s\n", algomap[i]); Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/config.h b/config.h /scm/dedup/file/config.h.gph bitreich.org 70 i@@ -1,5 +1,8 @@ Err bitreich.org 70 i-#define BLKSIZE_AVG ((size_t)(1ul << 21)) Err bitreich.org 70 i-#define BLKSIZE_MIN ((size_t)524288) Err bitreich.org 70 i-#define BLKSIZE_MAX ((size_t)8388608) Err bitreich.org 70 i-#define HASHMASK_BITS (BLKSIZE_AVG - 1) Err bitreich.org 70 i+#define ARCHIVEPATH "archive" Err bitreich.org 70 i+#define STORAGEPATH "storage" Err bitreich.org 70 i+#define MDSIZE 32 Err bitreich.org 70 i+#define BSIZEAVG ((size_t)(1ul << 21)) Err bitreich.org 70 i+#define BSIZEMIN ((size_t)524288) Err bitreich.org 70 i+#define BSIZEMAX ((size_t)8388608) Err bitreich.org 70 i+#define HMASKBITS (BSIZEAVG - 1) Err bitreich.org 70 i #define WINSIZE ((size_t)4095) Err bitreich.org 70 1diff --git a/config.mk b/config.mk /scm/dedup/file/config.mk.gph bitreich.org 70 i@@ -1,2 +1,3 @@ Err bitreich.org 70 i-#OPENMPCFLAGS = -fopenmp Err bitreich.org 70 i-#OPENMPLDLIBS = -lgomp Err bitreich.org 70 i+VERSION = 1.0 Err bitreich.org 70 i+PREFIX = /usr/local Err bitreich.org 70 i+MANPREFIX = $(PREFIX)/man Err bitreich.org 70 1diff --git a/dedup.h b/dedup.h /scm/dedup/file/dedup.h.gph bitreich.org 70 i@@ -1,233 +0,0 @@ Err bitreich.org 70 i-#include "config.h" Err bitreich.org 70 i- Err bitreich.org 70 i-#define SNAPSF ".snapshots" Err bitreich.org 70 i-#define STOREF ".store" Err bitreich.org 70 i- Err bitreich.org 70 i-/* Err bitreich.org 70 i- * These are the actual sizes of the structs in the Err bitreich.org 70 i- * file format itself. The types are serialized/deserialized Err bitreich.org 70 i- * using the helpers from types.c. Any modification made to Err bitreich.org 70 i- * the structs below will need to be reflected here and in types.c. Err bitreich.org 70 i- */ Err bitreich.org 70 i-#define MSG_SIZE 256 Err bitreich.org 70 i-#define MD_SIZE 32 Err bitreich.org 70 i- Err bitreich.org 70 i-#define SNAP_HDR_SIZE 104 Err bitreich.org 70 i-#define BLK_HDR_SIZE 16 Err bitreich.org 70 i-#define BLK_DESC_SIZE (MD_SIZE + 16) Err bitreich.org 70 i-#define SNAPSHOT_SIZE (8 + MSG_SIZE + MD_SIZE + 8) Err bitreich.org 70 i- Err bitreich.org 70 i-/* file format version */ Err bitreich.org 70 i-#define VER_MIN 2 Err bitreich.org 70 i-#define VER_MAJ 0 Err bitreich.org 70 i- Err bitreich.org 70 i-/* snapshot header and block header flags */ Err bitreich.org 70 i-#define VER_MIN_MASK 0xff Err bitreich.org 70 i-#define VER_MAJ_SHIFT 8 Err bitreich.org 70 i-#define VER_MAJ_MASK 0xff Err bitreich.org 70 i- Err bitreich.org 70 i-/* block header flags */ Err bitreich.org 70 i-#define HASH_ALGO_SHIFT 19 Err bitreich.org 70 i-#define HASH_ALGO_MASK 0x7 /* max 8 hash algos */ Err bitreich.org 70 i-#define COMPR_ALGO_SHIFT 16 Err bitreich.org 70 i-#define COMPR_ALGO_MASK 0x7 /* max 8 compression algos */ Err bitreich.org 70 i- Err bitreich.org 70 i-enum { Err bitreich.org 70 i- WALK_CONTINUE, Err bitreich.org 70 i- WALK_STOP Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-enum compr_algo { Err bitreich.org 70 i- COMPR_NONE, Err bitreich.org 70 i- COMPR_LZ4, Err bitreich.org 70 i- COMPR_SNAPPY, Err bitreich.org 70 i- NR_COMPRS, Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-enum hash_algo { Err bitreich.org 70 i- HASH_BLAKE2B, Err bitreich.org 70 i- HASH_BLAKE2BP, Err bitreich.org 70 i- HASH_BLAKE2S, Err bitreich.org 70 i- HASH_BLAKE2SP, Err bitreich.org 70 i- NR_HASHES, Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-struct chunker; Err bitreich.org 70 i-struct icache; Err bitreich.org 70 i- Err bitreich.org 70 i-struct stats { Err bitreich.org 70 i- uint64_t orig_size; /* original store size */ Err bitreich.org 70 i- uint64_t compr_size; /* compressed store size */ Err bitreich.org 70 i- uint64_t dedup_size; /* deduplicated store size */ Err bitreich.org 70 i- uint64_t min_blk_size; Err bitreich.org 70 i- uint64_t max_blk_size; Err bitreich.org 70 i- uint64_t nr_blks; /* number of unique blocks */ Err bitreich.org 70 i- uint64_t reserved[4]; Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-struct snap_hdr { Err bitreich.org 70 i- uint64_t flags; Err bitreich.org 70 i- uint64_t size; /* size of snapshots file */ Err bitreich.org 70 i- uint64_t nr_snaps; Err bitreich.org 70 i- struct stats st; Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-struct blk_hdr { Err bitreich.org 70 i- uint64_t flags; Err bitreich.org 70 i- uint64_t size; /* size of store file */ Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-struct blk_desc { Err bitreich.org 70 i- uint8_t md[MD_SIZE]; /* hash of block */ Err bitreich.org 70 i- uint64_t offset; /* offset into store file */ Err bitreich.org 70 i- uint64_t size; /* size of block */ Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-struct snap { Err bitreich.org 70 i- uint64_t size; /* size of snapshot (including block descriptors) */ Err bitreich.org 70 i- uint8_t msg[MSG_SIZE]; /* arbitrary message attached to snapshot */ Err bitreich.org 70 i- uint8_t md[MD_SIZE]; /* hash of snapshot (hash of all block descriptor hashes) */ Err bitreich.org 70 i- uint64_t nr_blk_descs; Err bitreich.org 70 i- struct blk_desc blk_desc[]; Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-struct compr_ctx { Err bitreich.org 70 i- struct compr_ops *ops; Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-struct hash_ctx { Err bitreich.org 70 i- union { Err bitreich.org 70 i- blake2b_state blake2b_ctx; Err bitreich.org 70 i- blake2bp_state blake2bp_ctx; Err bitreich.org 70 i- blake2s_state blake2s_ctx; Err bitreich.org 70 i- blake2sp_state blake2sp_ctx; Err bitreich.org 70 i- } u; Err bitreich.org 70 i- struct hash_ops *ops; Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-/* dedup.c */ Err bitreich.org 70 i-extern int verbose; Err bitreich.org 70 i- Err bitreich.org 70 i-/* chunker.c */ Err bitreich.org 70 i-struct chunker *alloc_chunker(int fd, size_t min_size, size_t max_size, Err bitreich.org 70 i- size_t mask, size_t win_size); Err bitreich.org 70 i-void free_chunker(struct chunker *chunker); Err bitreich.org 70 i-ssize_t fill_chunker(struct chunker *chunker); Err bitreich.org 70 i-uint8_t *get_chunk(struct chunker *chunker, size_t *chunk_size); Err bitreich.org 70 i-void drain_chunker(struct chunker *chunker); Err bitreich.org 70 i- Err bitreich.org 70 i-/* compress-none.c */ Err bitreich.org 70 i-int none_init(struct compr_ctx *ctx); Err bitreich.org 70 i-size_t none_size(struct compr_ctx *ctx, size_t n); Err bitreich.org 70 i-size_t none_compr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize); Err bitreich.org 70 i-size_t none_decompr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize); Err bitreich.org 70 i-int none_final(struct compr_ctx *ctx); Err bitreich.org 70 i- Err bitreich.org 70 i-/* compress-lz4.c */ Err bitreich.org 70 i-int lz4_init(struct compr_ctx *ctx); Err bitreich.org 70 i-size_t lz4_size(struct compr_ctx *ctx, size_t n); Err bitreich.org 70 i-size_t lz4_compr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize); Err bitreich.org 70 i-size_t lz4_decompr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize); Err bitreich.org 70 i-int lz4_final(struct compr_ctx *ctx); Err bitreich.org 70 i- Err bitreich.org 70 i-/* compress-snappy.c */ Err bitreich.org 70 i-int snappy_init(struct compr_ctx *ctx); Err bitreich.org 70 i-size_t snappy_size(struct compr_ctx *ctx, size_t n); Err bitreich.org 70 i-size_t snappy_compr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize); Err bitreich.org 70 i-size_t snappy_decompr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize); Err bitreich.org 70 i-int snappy_final(struct compr_ctx *ctx); Err bitreich.org 70 i- Err bitreich.org 70 i-/* compress.c */ Err bitreich.org 70 i-int compr_init(struct compr_ctx *ctx, int type); Err bitreich.org 70 i-int compr_size(struct compr_ctx *ctx, size_t n); Err bitreich.org 70 i-size_t compr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize); Err bitreich.org 70 i-size_t decompr(struct compr_ctx *ctx, const void *in, void *out, Err bitreich.org 70 i- size_t insize, size_t outsize); Err bitreich.org 70 i-int compr_final(struct compr_ctx *ctx); Err bitreich.org 70 i-int compr_name2type(char *name); Err bitreich.org 70 i-char *compr_type2name(int type); Err bitreich.org 70 i-void compr_list(int fd); Err bitreich.org 70 i- Err bitreich.org 70 i-/* hash-blake2b.c */ Err bitreich.org 70 i-int blake2bi(struct hash_ctx *ctx, size_t n); Err bitreich.org 70 i-int blake2bu(struct hash_ctx *ctx, const void *buf, size_t n); Err bitreich.org 70 i-int blake2bf(struct hash_ctx *ctx, void *buf, size_t n); Err bitreich.org 70 i- Err bitreich.org 70 i-/* hash-blake2bp.c */ Err bitreich.org 70 i-int blake2bpi(struct hash_ctx *ctx, size_t n); Err bitreich.org 70 i-int blake2bpu(struct hash_ctx *ctx, const void *buf, size_t n); Err bitreich.org 70 i-int blake2bpf(struct hash_ctx *ctx, void *buf, size_t n); Err bitreich.org 70 i- Err bitreich.org 70 i-/* hash-blake2s.c */ Err bitreich.org 70 i-int blake2si(struct hash_ctx *ctx, size_t n); Err bitreich.org 70 i-int blake2su(struct hash_ctx *ctx, const void *buf, size_t n); Err bitreich.org 70 i-int blake2sf(struct hash_ctx *ctx, void *buf, size_t n); Err bitreich.org 70 i- Err bitreich.org 70 i-/* hash-blake2sp.c */ Err bitreich.org 70 i-int blake2spi(struct hash_ctx *ctx, size_t n); Err bitreich.org 70 i-int blake2spu(struct hash_ctx *ctx, const void *buf, size_t n); Err bitreich.org 70 i-int blake2spf(struct hash_ctx *ctx, void *buf, size_t n); Err bitreich.org 70 i- Err bitreich.org 70 i-/* hash.c */ Err bitreich.org 70 i-int hash_init(struct hash_ctx *ctx, int type, size_t n); Err bitreich.org 70 i-int hash_update(struct hash_ctx *ctx, const void *buf, size_t n); Err bitreich.org 70 i-int hash_final(struct hash_ctx *ctx, void *buf, size_t n); Err bitreich.org 70 i-int hash_name2type(char *name); Err bitreich.org 70 i-char *hash_type2name(int type); Err bitreich.org 70 i-void hash_list(int fd); Err bitreich.org 70 i- Err bitreich.org 70 i-/* icache.c */ Err bitreich.org 70 i-struct icache *alloc_icache(void); Err bitreich.org 70 i-void free_icache(struct icache *icache); Err bitreich.org 70 i-void insert_icache(struct icache *icache, struct blk_desc *desc); Err bitreich.org 70 i-int lookup_icache(struct icache *icache, struct blk_desc *desc); Err bitreich.org 70 i-void icache_stats(struct icache *icache, unsigned long long *hits, Err bitreich.org 70 i- unsigned long long *misses); Err bitreich.org 70 i- Err bitreich.org 70 i-/* pack.c */ Err bitreich.org 70 i-int pack(unsigned char *dst, char *fmt, ...); Err bitreich.org 70 i- Err bitreich.org 70 i-/* unpack.c */ Err bitreich.org 70 i-int unpack(unsigned char *src, char *fmt, ...); Err bitreich.org 70 i- Err bitreich.org 70 i-/* types.c */ Err bitreich.org 70 i-void read_snap_hdr(int fd, struct snap_hdr *hdr); Err bitreich.org 70 i-void write_snap_hdr(int fd, struct snap_hdr *hdr); Err bitreich.org 70 i-void read_blk_hdr(int fd, struct blk_hdr *hdr); Err bitreich.org 70 i-void write_blk_hdr(int fd, struct blk_hdr *hdr); Err bitreich.org 70 i-void read_blk_desc(int fd, struct blk_desc *desc); Err bitreich.org 70 i-void write_blk_desc(int fd, struct blk_desc *desc); Err bitreich.org 70 i-void read_snap(int fd, struct snap *snap); Err bitreich.org 70 i-void read_snap_descs(int fd, struct snap *snap); Err bitreich.org 70 i-void write_snap(int fd, struct snap *snap); Err bitreich.org 70 i-void write_snap_blk_descs(int fd, struct snap *snap); Err bitreich.org 70 i- Err bitreich.org 70 i-/* utils.c */ Err bitreich.org 70 i-void str2bin(char *s, uint8_t *d); Err bitreich.org 70 i-off_t xlseek(int fd, off_t offset, int whence); Err bitreich.org 70 i-ssize_t xread(int fd, void *buf, size_t nbytes); Err bitreich.org 70 i-ssize_t xwrite(int fd, const void *buf, size_t nbytes); Err bitreich.org 70 i-void init_blk_hdr(struct blk_hdr *hdr, int compr_algo, int hash_algo); Err bitreich.org 70 i-void init_snap_hdr(struct snap_hdr *hdr); Err bitreich.org 70 i-void load_blk_hdr(int fd, struct blk_hdr *hdr, int *compr_algo, int *hash_algo); Err bitreich.org 70 i-void load_snap_hdr(int fd, struct snap_hdr *hdr); Err bitreich.org 70 i-struct snap *alloc_snap(void); Err bitreich.org 70 i-void free_snap(struct snap *snap); Err bitreich.org 70 i-struct snap *grow_snap(struct snap *snap, uint64_t nr_blk_descs); Err bitreich.org 70 i-void append_snap(int fd, struct snap_hdr *hdr, struct snap *snap); Err bitreich.org 70 i-void hash_snap(struct snap *snap, uint8_t *md, int hash_algo); Err bitreich.org 70 i-void walk_snap(int fd, struct snap_hdr *hdr, Err bitreich.org 70 i- int (*fn)(struct snap *, void *), void *arg); Err bitreich.org 70 i-uint8_t *alloc_buf(size_t size); Err bitreich.org 70 i-void free_buf(uint8_t *buf); Err bitreich.org 70 i-void read_blk(int fd, uint8_t *buf, struct blk_desc *blk_desc); Err bitreich.org 70 i-void append_blk(int fd, struct blk_hdr *hdr, uint8_t *buf, Err bitreich.org 70 i- struct blk_desc *blk_desc); Err bitreich.org 70 i-void hash_blk(uint8_t *buf, size_t size, uint8_t *md, int hash_algo); Err bitreich.org 70 1diff --git a/dup-check.1 b/dup-check.1 /scm/dedup/file/dup-check.1.gph bitreich.org 70 i@@ -1,25 +0,0 @@ Err bitreich.org 70 i-.Dd April 18, 2019 Err bitreich.org 70 i-.Dt DUP-CHECK 1 Err bitreich.org 70 i-.Os Err bitreich.org 70 i-.Sh NAME Err bitreich.org 70 i-.Nm dup-check Err bitreich.org 70 i-.Nd Perform consistency checks on a dedup repo Err bitreich.org 70 i-.Sh SYNOPSIS Err bitreich.org 70 i-.Nm dup-check Err bitreich.org 70 i-.Op Fl v Err bitreich.org 70 i-.Op repo Err bitreich.org 70 i-.Sh DESCRIPTION Err bitreich.org 70 i-.Nm Err bitreich.org 70 i-performs consistency checks on a dedup repo. Err bitreich.org 70 i-If no Err bitreich.org 70 i-.Ar repo Err bitreich.org 70 i-is specified, then the current directory Err bitreich.org 70 i-is assumed to be the repository. Err bitreich.org 70 i-.Sh OPTIONS Err bitreich.org 70 i-.Bl -tag -width "-v" Err bitreich.org 70 i-.It Fl v Err bitreich.org 70 i-Enable verbose mode. Err bitreich.org 70 i-.El Err bitreich.org 70 i-.Sh AUTHORS Err bitreich.org 70 i-.An Dimitris Papastamos Aq Mt sin@2f30.org , Err bitreich.org 70 i-.An z3bra Aq Mt contactatz3bradotorg . Err bitreich.org 70 1diff --git a/dup-check.c b/dup-check.c /scm/dedup/file/dup-check.c.gph bitreich.org 70 i@@ -1,157 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "arg.h" Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-static struct snap_hdr snap_hdr; Err bitreich.org 70 i-static struct blk_hdr blk_hdr; Err bitreich.org 70 i-static int ifd; Err bitreich.org 70 i-static int sfd; Err bitreich.org 70 i-static int hash_algo = HASH_BLAKE2B; Err bitreich.org 70 i-static int compr_algo = COMPR_LZ4; Err bitreich.org 70 i- Err bitreich.org 70 i-int verbose; Err bitreich.org 70 i-char *argv0; Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-print_md(FILE *fp, uint8_t *md, size_t size) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- for (i = 0; i < size; i++) Err bitreich.org 70 i- fprintf(fp, "%02x", md[i]); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-/* Err bitreich.org 70 i- * Hash every block referenced by the given snapshot Err bitreich.org 70 i- * and compare its hash with the one stored in the corresponding Err bitreich.org 70 i- * block descriptor. Err bitreich.org 70 i- */ Err bitreich.org 70 i-static int Err bitreich.org 70 i-check_snap(struct snap *snap, void *arg) Err bitreich.org 70 i-{ Err bitreich.org 70 i- struct compr_ctx ctx; Err bitreich.org 70 i- uint8_t *buf; Err bitreich.org 70 i- int *ret = arg; Err bitreich.org 70 i- uint64_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if (verbose > 0) { Err bitreich.org 70 i- fprintf(stderr, "Checking snapshot: "); Err bitreich.org 70 i- print_md(stderr, snap->md, sizeof(snap->md)); Err bitreich.org 70 i- fputc('\n', stderr); Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- if (compr_init(&ctx, compr_algo) < 0) Err bitreich.org 70 i- errx(1, "compr_init failed"); Err bitreich.org 70 i- buf = alloc_buf(compr_size(&ctx, BLKSIZE_MAX)); Err bitreich.org 70 i- for (i = 0; i < snap->nr_blk_descs; i++) { Err bitreich.org 70 i- uint8_t md[MD_SIZE]; Err bitreich.org 70 i- struct blk_desc *blk_desc; Err bitreich.org 70 i- Err bitreich.org 70 i- blk_desc = &snap->blk_desc[i]; Err bitreich.org 70 i- read_blk(sfd, buf, blk_desc); Err bitreich.org 70 i- hash_blk(buf, blk_desc->size, md, hash_algo); Err bitreich.org 70 i- Err bitreich.org 70 i- if (memcmp(blk_desc->md, md, sizeof(blk_desc->md)) == 0) Err bitreich.org 70 i- continue; Err bitreich.org 70 i- Err bitreich.org 70 i- fprintf(stderr, "Block hash mismatch\n"); Err bitreich.org 70 i- fprintf(stderr, " Expected hash: "); Err bitreich.org 70 i- print_md(stderr, blk_desc->md, sizeof(blk_desc->md)); Err bitreich.org 70 i- fputc('\n', stderr); Err bitreich.org 70 i- fprintf(stderr, " Actual hash: "); Err bitreich.org 70 i- print_md(stderr, md, sizeof(md)); Err bitreich.org 70 i- fputc('\n', stderr); Err bitreich.org 70 i- fprintf(stderr, " Offset: %llu\n", Err bitreich.org 70 i- (unsigned long long)blk_desc->offset); Err bitreich.org 70 i- fprintf(stderr, " Size: %llu\n", Err bitreich.org 70 i- (unsigned long long)blk_desc->size); Err bitreich.org 70 i- *ret = -1; Err bitreich.org 70 i- } Err bitreich.org 70 i- free_buf(buf); Err bitreich.org 70 i- compr_final(&ctx); Err bitreich.org 70 i- return WALK_CONTINUE; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-init(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- ifd = open(SNAPSF, O_RDONLY, 0600); Err bitreich.org 70 i- if (ifd < 0) Err bitreich.org 70 i- err(1, "open %s", SNAPSF); Err bitreich.org 70 i- Err bitreich.org 70 i- sfd = open(STOREF, O_RDONLY, 0600); Err bitreich.org 70 i- if (sfd < 0) Err bitreich.org 70 i- err(1, "open %s", STOREF); Err bitreich.org 70 i- Err bitreich.org 70 i- if (flock(ifd, LOCK_NB | LOCK_EX) < 0 || Err bitreich.org 70 i- flock(sfd, LOCK_NB | LOCK_EX) < 0) Err bitreich.org 70 i- err(1, "flock"); Err bitreich.org 70 i- Err bitreich.org 70 i- xlseek(ifd, 0, SEEK_SET); Err bitreich.org 70 i- load_snap_hdr(ifd, &snap_hdr); Err bitreich.org 70 i- xlseek(sfd, 0, SEEK_SET); Err bitreich.org 70 i- load_blk_hdr(sfd, &blk_hdr, &compr_algo, &hash_algo); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-term(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- close(ifd); Err bitreich.org 70 i- close(sfd); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-usage(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- fprintf(stderr, "usage: %s [-v] [repo]\n", argv0); Err bitreich.org 70 i- exit(1); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-main(int argc, char *argv[]) Err bitreich.org 70 i-{ Err bitreich.org 70 i- char *repo = NULL; Err bitreich.org 70 i- int ret; Err bitreich.org 70 i- Err bitreich.org 70 i- ARGBEGIN { Err bitreich.org 70 i- case 'v': Err bitreich.org 70 i- verbose++; Err bitreich.org 70 i- break; Err bitreich.org 70 i- default: Err bitreich.org 70 i- usage(); Err bitreich.org 70 i- } ARGEND Err bitreich.org 70 i- Err bitreich.org 70 i- switch (argc) { Err bitreich.org 70 i- case 0: Err bitreich.org 70 i- repo = "."; Err bitreich.org 70 i- break; Err bitreich.org 70 i- case 1: Err bitreich.org 70 i- repo = argv[0]; Err bitreich.org 70 i- break; Err bitreich.org 70 i- default: Err bitreich.org 70 i- usage(); Err bitreich.org 70 i- }; Err bitreich.org 70 i- Err bitreich.org 70 i- if (chdir(repo) < 0) Err bitreich.org 70 i- err(1, "chdir: %s", repo); Err bitreich.org 70 i- Err bitreich.org 70 i- init(); Err bitreich.org 70 i- ret = 0; Err bitreich.org 70 i- walk_snap(ifd, &snap_hdr, check_snap, &ret); Err bitreich.org 70 i- if (ret != 0) Err bitreich.org 70 i- errx(1, "%s or %s is corrupted", SNAPSF, STOREF); Err bitreich.org 70 i- term(); Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/dup-info.1 b/dup-info.1 /scm/dedup/file/dup-info.1.gph bitreich.org 70 i@@ -1,37 +0,0 @@ Err bitreich.org 70 i-.Dd April 18, 2019 Err bitreich.org 70 i-.Dt DUP-INFO 1 Err bitreich.org 70 i-.Os Err bitreich.org 70 i-.Sh NAME Err bitreich.org 70 i-.Nm dup-info Err bitreich.org 70 i-.Nd Print information about a dedup repository Err bitreich.org 70 i-.Sh SYNOPSIS Err bitreich.org 70 i-.Nm dup-info Err bitreich.org 70 i-.Op Fl tv Err bitreich.org 70 i-.Op repo Err bitreich.org 70 i-.Sh DESCRIPTION Err bitreich.org 70 i-.Nm Err bitreich.org 70 i-prints information about a dedup repository. Err bitreich.org 70 i-If no Err bitreich.org 70 i-.Ar repo Err bitreich.org 70 i-is specified, then the current directory Err bitreich.org 70 i-is assumed to be the repository. Err bitreich.org 70 i-.Sh OPTIONS Err bitreich.org 70 i-.Bl -tag -width "-v" Err bitreich.org 70 i-.It Fl t Err bitreich.org 70 i-Enable terse mode. Err bitreich.org 70 i-The output fields are as follows: Err bitreich.org 70 i-.br Err bitreich.org 70 i-[original dataset size] Err bitreich.org 70 i-[compressed dataset size] Err bitreich.org 70 i-[deduplicated dataset size] Err bitreich.org 70 i-[deduplication ratio] Err bitreich.org 70 i-[min block size] Err bitreich.org 70 i-[average block size] Err bitreich.org 70 i-[max block size] Err bitreich.org 70 i-[number of unique blocks] Err bitreich.org 70 i-.It Fl v Err bitreich.org 70 i-Enable verbose mode. Err bitreich.org 70 i-.El Err bitreich.org 70 i-.Sh AUTHORS Err bitreich.org 70 i-.An Dimitris Papastamos Aq Mt sin@2f30.org , Err bitreich.org 70 i-.An z3bra Aq Mt contactatz3bradotorg . Err bitreich.org 70 1diff --git a/dup-info.c b/dup-info.c /scm/dedup/file/dup-info.c.gph bitreich.org 70 i@@ -1,141 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "arg.h" Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-static struct snap_hdr snap_hdr; Err bitreich.org 70 i-static struct blk_hdr blk_hdr; Err bitreich.org 70 i-static int ifd; Err bitreich.org 70 i-static int sfd; Err bitreich.org 70 i-static int hash_algo = HASH_BLAKE2B; Err bitreich.org 70 i-static int compr_algo = COMPR_LZ4; Err bitreich.org 70 i- Err bitreich.org 70 i-int verbose; Err bitreich.org 70 i-char *argv0; Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-print_info(int tflag) Err bitreich.org 70 i-{ Err bitreich.org 70 i- struct stats *st = &snap_hdr.st; Err bitreich.org 70 i- Err bitreich.org 70 i- if (verbose > 0) { Err bitreich.org 70 i- fprintf(stderr, "Compression algorithm: %s\n", Err bitreich.org 70 i- compr_type2name(compr_algo)); Err bitreich.org 70 i- fprintf(stderr, "Hash algorithm: %s\n", Err bitreich.org 70 i- hash_type2name(hash_algo)); Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- if (st->nr_blks == 0) Err bitreich.org 70 i- return; Err bitreich.org 70 i- Err bitreich.org 70 i- if (!tflag) { Err bitreich.org 70 i- fprintf(stderr, "Original size: %llu bytes\n", Err bitreich.org 70 i- (unsigned long long)st->orig_size); Err bitreich.org 70 i- fprintf(stderr, "Compressed size: %llu bytes\n", Err bitreich.org 70 i- (unsigned long long)st->compr_size); Err bitreich.org 70 i- fprintf(stderr, "Deduplicated size: %llu bytes\n", Err bitreich.org 70 i- (unsigned long long)st->dedup_size); Err bitreich.org 70 i- fprintf(stderr, "Deduplication ratio: %.2f\n", Err bitreich.org 70 i- (double)st->orig_size / st->dedup_size); Err bitreich.org 70 i- fprintf(stderr, "Min/avg/max block size: %llu/%llu/%llu bytes\n", Err bitreich.org 70 i- (unsigned long long)st->min_blk_size, Err bitreich.org 70 i- (unsigned long long)st->dedup_size / st->nr_blks, Err bitreich.org 70 i- (unsigned long long)st->max_blk_size); Err bitreich.org 70 i- fprintf(stderr, "Number of unique blocks: %llu\n", Err bitreich.org 70 i- (unsigned long long)st->nr_blks); Err bitreich.org 70 i- } else { Err bitreich.org 70 i- /* terse mode */ Err bitreich.org 70 i- fprintf(stderr, "%llu %llu %llu %.2f %llu %llu %llu %llu\n", Err bitreich.org 70 i- (unsigned long long)st->orig_size, Err bitreich.org 70 i- (unsigned long long)st->compr_size, Err bitreich.org 70 i- (unsigned long long)st->dedup_size, Err bitreich.org 70 i- (double)st->orig_size / st->dedup_size, Err bitreich.org 70 i- (unsigned long long)st->min_blk_size, Err bitreich.org 70 i- (unsigned long long)st->dedup_size / st->nr_blks, Err bitreich.org 70 i- (unsigned long long)st->max_blk_size, Err bitreich.org 70 i- (unsigned long long)st->nr_blks); Err bitreich.org 70 i- } Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-init(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- ifd = open(SNAPSF, O_RDONLY, 0600); Err bitreich.org 70 i- if (ifd < 0) Err bitreich.org 70 i- err(1, "open %s", SNAPSF); Err bitreich.org 70 i- Err bitreich.org 70 i- sfd = open(STOREF, O_RDONLY, 0600); Err bitreich.org 70 i- if (sfd < 0) Err bitreich.org 70 i- err(1, "open %s", STOREF); Err bitreich.org 70 i- Err bitreich.org 70 i- if (flock(ifd, LOCK_NB | LOCK_EX) < 0 || Err bitreich.org 70 i- flock(sfd, LOCK_NB | LOCK_EX) < 0) Err bitreich.org 70 i- err(1, "flock"); Err bitreich.org 70 i- Err bitreich.org 70 i- xlseek(ifd, 0, SEEK_SET); Err bitreich.org 70 i- load_snap_hdr(ifd, &snap_hdr); Err bitreich.org 70 i- xlseek(sfd, 0, SEEK_SET); Err bitreich.org 70 i- load_blk_hdr(sfd, &blk_hdr, &compr_algo, &hash_algo); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-term(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- close(ifd); Err bitreich.org 70 i- close(sfd); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-usage(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- fprintf(stderr, "usage: %s [-tv] [repo]\n", argv0); Err bitreich.org 70 i- exit(1); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-main(int argc, char *argv[]) Err bitreich.org 70 i-{ Err bitreich.org 70 i- char *repo = NULL; Err bitreich.org 70 i- int tflag = 0; Err bitreich.org 70 i- Err bitreich.org 70 i- ARGBEGIN { Err bitreich.org 70 i- case 't': Err bitreich.org 70 i- tflag = 1; Err bitreich.org 70 i- break; Err bitreich.org 70 i- case 'v': Err bitreich.org 70 i- verbose++; Err bitreich.org 70 i- break; Err bitreich.org 70 i- default: Err bitreich.org 70 i- usage(); Err bitreich.org 70 i- } ARGEND Err bitreich.org 70 i- Err bitreich.org 70 i- switch (argc) { Err bitreich.org 70 i- case 0: Err bitreich.org 70 i- repo = "."; Err bitreich.org 70 i- break; Err bitreich.org 70 i- case 1: Err bitreich.org 70 i- repo = argv[0]; Err bitreich.org 70 i- break; Err bitreich.org 70 i- default: Err bitreich.org 70 i- usage(); Err bitreich.org 70 i- }; Err bitreich.org 70 i- Err bitreich.org 70 i- if (chdir(repo) < 0) Err bitreich.org 70 i- err(1, "chdir: %s", repo); Err bitreich.org 70 i- Err bitreich.org 70 i- init(); Err bitreich.org 70 i- print_info(tflag); Err bitreich.org 70 i- term(); Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/dup-init.1 b/dup-init.1 /scm/dedup/file/dup-init.1.gph bitreich.org 70 i@@ -24,15 +24,15 @@ Enable verbose mode. Err bitreich.org 70 i .It Fl H Ar hash Err bitreich.org 70 i The cryptographic hash function used to identify Err bitreich.org 70 i unique blocks in the store. Err bitreich.org 70 i-The supported hash functions are blake2b, blake2bp, blake2s and blake2sp. Err bitreich.org 70 i+The supported hash functions are blake2b. Err bitreich.org 70 i This flag only has an effect when initializing the repository. Err bitreich.org 70 i By default blake2b is used. Err bitreich.org 70 i .It Fl Z Ar compressor Err bitreich.org 70 i The compressor function used to compress the blocks Err bitreich.org 70 i in the store. Err bitreich.org 70 i-The supported compressor functions are none, lz4 and snappy. Err bitreich.org 70 i+The supported compressor functions are none and snappy. Err bitreich.org 70 i This flag only has an effect when initializing the repository. Err bitreich.org 70 i-By default lz4 is used. Err bitreich.org 70 i+By default snappy is used. Err bitreich.org 70 i .El Err bitreich.org 70 i .Sh AUTHORS Err bitreich.org 70 i .An Dimitris Papastamos Aq Mt sin@2f30.org , Err bitreich.org 70 1diff --git a/dup-init.c b/dup-init.c /scm/dedup/file/dup-init.c.gph bitreich.org 70 i@@ -1,67 +1,21 @@ Err bitreich.org 70 i #include Err bitreich.org 70 i #include Err bitreich.org 70 i-#include Err bitreich.org 70 i Err bitreich.org 70 i #include Err bitreich.org 70 i #include Err bitreich.org 70 i #include Err bitreich.org 70 i-#include Err bitreich.org 70 i #include Err bitreich.org 70 i-#include Err bitreich.org 70 i #include Err bitreich.org 70 i Err bitreich.org 70 i #include "arg.h" Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-static struct snap_hdr snap_hdr; Err bitreich.org 70 i-static struct blk_hdr blk_hdr; Err bitreich.org 70 i-static int ifd; Err bitreich.org 70 i-static int sfd; Err bitreich.org 70 i-static int hash_algo = HASH_BLAKE2B; Err bitreich.org 70 i-static int compr_algo = COMPR_LZ4; Err bitreich.org 70 i+#include "config.h" Err bitreich.org 70 i+#include "block.h" Err bitreich.org 70 i+#include "snap.h" Err bitreich.org 70 i Err bitreich.org 70 i int verbose; Err bitreich.org 70 i char *argv0; Err bitreich.org 70 i Err bitreich.org 70 i static void Err bitreich.org 70 i-init(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- int flags; Err bitreich.org 70 i- Err bitreich.org 70 i- flags = O_RDWR | O_CREAT | O_EXCL; Err bitreich.org 70 i- ifd = open(SNAPSF, flags, 0600); Err bitreich.org 70 i- if (ifd < 0) Err bitreich.org 70 i- err(1, "open %s", SNAPSF); Err bitreich.org 70 i- Err bitreich.org 70 i- sfd = open(STOREF, flags, 0600); Err bitreich.org 70 i- if (sfd < 0) Err bitreich.org 70 i- err(1, "open %s", STOREF); Err bitreich.org 70 i- Err bitreich.org 70 i- if (flock(ifd, LOCK_NB | LOCK_EX) < 0 || Err bitreich.org 70 i- flock(sfd, LOCK_NB | LOCK_EX) < 0) Err bitreich.org 70 i- err(1, "flock"); Err bitreich.org 70 i- Err bitreich.org 70 i- init_snap_hdr(&snap_hdr); Err bitreich.org 70 i- init_blk_hdr(&blk_hdr, compr_algo, hash_algo); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-term(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- xlseek(ifd, 0, SEEK_SET); Err bitreich.org 70 i- write_snap_hdr(ifd, &snap_hdr); Err bitreich.org 70 i- xlseek(sfd, 0, SEEK_SET); Err bitreich.org 70 i- write_blk_hdr(sfd, &blk_hdr); Err bitreich.org 70 i- Err bitreich.org 70 i- fsync(ifd); Err bitreich.org 70 i- fsync(sfd); Err bitreich.org 70 i- Err bitreich.org 70 i- close(ifd); Err bitreich.org 70 i- close(sfd); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i usage(void) Err bitreich.org 70 i { Err bitreich.org 70 i fprintf(stderr, "usage: %s [-v] [-H hash] [-Z compressor] [repo]\n", argv0); Err bitreich.org 70 i@@ -71,29 +25,19 @@ usage(void) Err bitreich.org 70 i int Err bitreich.org 70 i main(int argc, char *argv[]) Err bitreich.org 70 i { Err bitreich.org 70 i- char *hash_name = NULL, *compr_name = NULL; Err bitreich.org 70 i+ struct bctx *bctx; /* block context */ Err bitreich.org 70 i+ struct bparam bpar; Err bitreich.org 70 i char *repo; Err bitreich.org 70 i Err bitreich.org 70 i+ bpar.calgo = bparamdef()->calgo; Err bitreich.org 70 i+ bpar.halgo = bparamdef()->halgo; Err bitreich.org 70 i+ Err bitreich.org 70 i ARGBEGIN { Err bitreich.org 70 i case 'H': Err bitreich.org 70 i- hash_name = EARGF(usage()); Err bitreich.org 70 i- if (strcmp(hash_name, "?") == 0) { Err bitreich.org 70 i- hash_list(STDERR_FILENO); Err bitreich.org 70 i- return 0; Err bitreich.org 70 i- } Err bitreich.org 70 i- hash_algo = hash_name2type(hash_name); Err bitreich.org 70 i- if (hash_algo < 0) Err bitreich.org 70 i- errx(1, "unknown hash: %s", hash_name); Err bitreich.org 70 i+ bpar.halgo = EARGF(usage()); Err bitreich.org 70 i break; Err bitreich.org 70 i case 'Z': Err bitreich.org 70 i- compr_name = EARGF(usage()); Err bitreich.org 70 i- if (strcmp(compr_name, "?") == 0) { Err bitreich.org 70 i- compr_list(STDERR_FILENO); Err bitreich.org 70 i- return 0; Err bitreich.org 70 i- } Err bitreich.org 70 i- compr_algo = compr_name2type(compr_name); Err bitreich.org 70 i- if (compr_algo < 0) Err bitreich.org 70 i- errx(1, "unknown compressor: %s", compr_name); Err bitreich.org 70 i+ bpar.calgo = EARGF(usage()); Err bitreich.org 70 i break; Err bitreich.org 70 i case 'v': Err bitreich.org 70 i verbose++; Err bitreich.org 70 i@@ -117,7 +61,10 @@ main(int argc, char *argv[]) Err bitreich.org 70 i if (chdir(repo) < 0) Err bitreich.org 70 i err(1, "chdir: %s", repo); Err bitreich.org 70 i Err bitreich.org 70 i- init(); Err bitreich.org 70 i- term(); Err bitreich.org 70 i+ mkdir(ARCHIVEPATH, 0700); Err bitreich.org 70 i+ if (bcreat(STORAGEPATH, 0600, &bpar, &bctx) < 0) Err bitreich.org 70 i+ errx(1, "bcreat: failed"); Err bitreich.org 70 i+ if (bclose(bctx) < 0) Err bitreich.org 70 i+ errx(1, "bclose: failed"); Err bitreich.org 70 i return 0; Err bitreich.org 70 i } Err bitreich.org 70 1diff --git a/dup-list.1 b/dup-list.1 /scm/dedup/file/dup-list.1.gph bitreich.org 70 i@@ -1,25 +0,0 @@ Err bitreich.org 70 i-.Dd April 18, 2019 Err bitreich.org 70 i-.Dt DUP-LIST 1 Err bitreich.org 70 i-.Os Err bitreich.org 70 i-.Sh NAME Err bitreich.org 70 i-.Nm dup-list Err bitreich.org 70 i-.Nd List snapshots from a dedup repository Err bitreich.org 70 i-.Sh SYNOPSIS Err bitreich.org 70 i-.Nm dup-list Err bitreich.org 70 i-.Op Fl v Err bitreich.org 70 i-.Op repo Err bitreich.org 70 i-.Sh DESCRIPTION Err bitreich.org 70 i-.Nm Err bitreich.org 70 i-lists snapshots from a dedup repository. Err bitreich.org 70 i-If no Err bitreich.org 70 i-.Ar repo Err bitreich.org 70 i-is specified, then the current directory Err bitreich.org 70 i-is assumed to be the repository. Err bitreich.org 70 i-.Sh OPTIONS Err bitreich.org 70 i-.Bl -tag -width "-v" Err bitreich.org 70 i-.It Fl v Err bitreich.org 70 i-Enable verbose mode. Err bitreich.org 70 i-.El Err bitreich.org 70 i-.Sh AUTHORS Err bitreich.org 70 i-.An Dimitris Papastamos Aq Mt sin@2f30.org , Err bitreich.org 70 i-.An z3bra Aq Mt contactatz3bradotorg . Err bitreich.org 70 1diff --git a/dup-list.c b/dup-list.c /scm/dedup/file/dup-list.c.gph bitreich.org 70 i@@ -1,113 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "arg.h" Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-static struct snap_hdr snap_hdr; Err bitreich.org 70 i-static struct blk_hdr blk_hdr; Err bitreich.org 70 i-static int ifd; Err bitreich.org 70 i-static int sfd; Err bitreich.org 70 i-static int hash_algo = HASH_BLAKE2B; Err bitreich.org 70 i-static int compr_algo = COMPR_LZ4; Err bitreich.org 70 i- Err bitreich.org 70 i-int verbose; Err bitreich.org 70 i-char *argv0; Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-print_md(FILE *fp, uint8_t *md, size_t size) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- for (i = 0; i < size; i++) Err bitreich.org 70 i- fprintf(fp, "%02x", md[i]); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static int Err bitreich.org 70 i-list(struct snap *snap, void *arg) Err bitreich.org 70 i-{ Err bitreich.org 70 i- print_md(stdout, snap->md, sizeof(snap->md)); Err bitreich.org 70 i- if (snap->msg[0] != '\0') Err bitreich.org 70 i- printf("\t%s\n", snap->msg); Err bitreich.org 70 i- else Err bitreich.org 70 i- putchar('\n'); Err bitreich.org 70 i- return WALK_CONTINUE; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-init(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- ifd = open(SNAPSF, O_RDONLY, 0600); Err bitreich.org 70 i- if (ifd < 0) Err bitreich.org 70 i- err(1, "open %s", SNAPSF); Err bitreich.org 70 i- Err bitreich.org 70 i- sfd = open(STOREF, O_RDONLY, 0600); Err bitreich.org 70 i- if (sfd < 0) Err bitreich.org 70 i- err(1, "open %s", STOREF); Err bitreich.org 70 i- Err bitreich.org 70 i- if (flock(ifd, LOCK_NB | LOCK_EX) < 0 || Err bitreich.org 70 i- flock(sfd, LOCK_NB | LOCK_EX) < 0) Err bitreich.org 70 i- err(1, "flock"); Err bitreich.org 70 i- Err bitreich.org 70 i- xlseek(ifd, 0, SEEK_SET); Err bitreich.org 70 i- load_snap_hdr(ifd, &snap_hdr); Err bitreich.org 70 i- xlseek(sfd, 0, SEEK_SET); Err bitreich.org 70 i- load_blk_hdr(sfd, &blk_hdr, &compr_algo, &hash_algo); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-term(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- close(ifd); Err bitreich.org 70 i- close(sfd); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-usage(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- fprintf(stderr, "usage: %s [-v] [repo]\n", argv0); Err bitreich.org 70 i- exit(1); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-main(int argc, char *argv[]) Err bitreich.org 70 i-{ Err bitreich.org 70 i- char *repo = NULL; Err bitreich.org 70 i- Err bitreich.org 70 i- ARGBEGIN { Err bitreich.org 70 i- case 'v': Err bitreich.org 70 i- verbose++; Err bitreich.org 70 i- break; Err bitreich.org 70 i- default: Err bitreich.org 70 i- usage(); Err bitreich.org 70 i- } ARGEND Err bitreich.org 70 i- Err bitreich.org 70 i- switch (argc) { Err bitreich.org 70 i- case 0: Err bitreich.org 70 i- repo = "."; Err bitreich.org 70 i- break; Err bitreich.org 70 i- case 1: Err bitreich.org 70 i- repo = argv[0]; Err bitreich.org 70 i- break; Err bitreich.org 70 i- default: Err bitreich.org 70 i- usage(); Err bitreich.org 70 i- }; Err bitreich.org 70 i- Err bitreich.org 70 i- if (chdir(repo) < 0) Err bitreich.org 70 i- err(1, "chdir: %s", repo); Err bitreich.org 70 i- Err bitreich.org 70 i- init(); Err bitreich.org 70 i- walk_snap(ifd, &snap_hdr, list, NULL); Err bitreich.org 70 i- term(); Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/dup-migrate b/dup-migrate /scm/dedup/file/dup-migrate.gph bitreich.org 70 i@@ -1,28 +0,0 @@ Err bitreich.org 70 i-#!/bin/sh Err bitreich.org 70 i-# Err bitreich.org 70 i-# Migrate an old dedup repo to a new one. Err bitreich.org 70 i-# This is useful when there is an ABI break Err bitreich.org 70 i-# in the deduplication repository file format. Err bitreich.org 70 i- Err bitreich.org 70 i-set -e Err bitreich.org 70 i- Err bitreich.org 70 i-usage() Err bitreich.org 70 i-{ Err bitreich.org 70 i- echo usage: dup-migrate old-repo new-repo >&2 Err bitreich.org 70 i- exit 1 Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-if [ ! "$#" -eq 2 ] Err bitreich.org 70 i-then Err bitreich.org 70 i- usage Err bitreich.org 70 i-fi Err bitreich.org 70 i- Err bitreich.org 70 i-oldrepo="$1" Err bitreich.org 70 i-newrepo="$2" Err bitreich.org 70 i- Err bitreich.org 70 i-dup-init "$newrepo" Err bitreich.org 70 i-dup-list-old "$oldrepo" | awk '{print $1}' | while read id Err bitreich.org 70 i-do Err bitreich.org 70 i- dup-unpack-old "$id" "$oldrepo" | dup-pack "$newrepo" Err bitreich.org 70 i-done Err bitreich.org 70 i-sync Err bitreich.org 70 1diff --git a/dup-migrate.1 b/dup-migrate.1 /scm/dedup/file/dup-migrate.1.gph bitreich.org 70 i@@ -1,26 +0,0 @@ Err bitreich.org 70 i-.Dd April 18, 2019 Err bitreich.org 70 i-.Dt DUP-MIGRATE 1 Err bitreich.org 70 i-.Os Err bitreich.org 70 i-.Sh NAME Err bitreich.org 70 i-.Nm dup-migrate Err bitreich.org 70 i-.Nd Migrate a dedup repository Err bitreich.org 70 i-.Sh SYNOPSIS Err bitreich.org 70 i-.Nm dup-migrate Err bitreich.org 70 i-.Ar old-repo Err bitreich.org 70 i-.Ar new-repo Err bitreich.org 70 i-.Sh DESCRIPTION Err bitreich.org 70 i-.Nm Err bitreich.org 70 i-migrates the Err bitreich.org 70 i-.Ar old-repo Err bitreich.org 70 i-to the Err bitreich.org 70 i-.Ar new-repo . Err bitreich.org 70 i-The Err bitreich.org 70 i-.Nm Err bitreich.org 70 i-script requires that the dup-list-old and Err bitreich.org 70 i-dup-unpack-old binaries are in the PATH. Err bitreich.org 70 i-These should be the most up to date binaries Err bitreich.org 70 i-that can operate on the Err bitreich.org 70 i-.Ar old-repo . Err bitreich.org 70 i-.Sh AUTHORS Err bitreich.org 70 i-.An Dimitris Papastamos Aq Mt sin@2f30.org , Err bitreich.org 70 i-.An z3bra Aq Mt contactatz3bradotorg . Err bitreich.org 70 1diff --git a/dup-pack.1 b/dup-pack.1 /scm/dedup/file/dup-pack.1.gph bitreich.org 70 i@@ -1,4 +1,4 @@ Err bitreich.org 70 i-.Dd April 18, 2019 Err bitreich.org 70 i+.Dd April 25, 2019 Err bitreich.org 70 i .Dt DUP-PACK 1 Err bitreich.org 70 i .Os Err bitreich.org 70 i .Sh NAME Err bitreich.org 70 i@@ -7,15 +7,14 @@ Err bitreich.org 70 i .Sh SYNOPSIS Err bitreich.org 70 i .Nm dup-pack Err bitreich.org 70 i .Op Fl v Err bitreich.org 70 i-.Op Fl m Ar message Err bitreich.org 70 i-.Op repo Err bitreich.org 70 i+.Op Fl r Ar repo Err bitreich.org 70 i+.Ar name Err bitreich.org 70 i .Sh DESCRIPTION Err bitreich.org 70 i .Nm Err bitreich.org 70 i deduplicates data from stdin. Err bitreich.org 70 i-If no Err bitreich.org 70 i-.Ar repo Err bitreich.org 70 i-is specified, then the current directory Err bitreich.org 70 i-is assumed to be the repository. Err bitreich.org 70 i+It creates a snapshot with the given Err bitreich.org 70 i+.Ar name Err bitreich.org 70 i+and stores it in the repository. Err bitreich.org 70 i .Pp Err bitreich.org 70 i .Nm Err bitreich.org 70 i does not track any file metadata so to deduplicate Err bitreich.org 70 i@@ -24,11 +23,12 @@ directory trees, an archival tool like Err bitreich.org 70 i should be used and piped into Err bitreich.org 70 i .Nm . Err bitreich.org 70 i .Sh OPTIONS Err bitreich.org 70 i-.Bl -tag -width "-m message" Err bitreich.org 70 i+.Bl -tag -width "-r repo" Err bitreich.org 70 i+.It Fl r Ar repo Err bitreich.org 70 i+Set repository directory. Err bitreich.org 70 i+By default the current working directory is used. Err bitreich.org 70 i .It Fl v Err bitreich.org 70 i Enable verbose mode. Err bitreich.org 70 i-.It Fl m Ar message Err bitreich.org 70 i-Attach a descriptive message to the snapshot. Err bitreich.org 70 i .El Err bitreich.org 70 i .Sh AUTHORS Err bitreich.org 70 i .An Dimitris Papastamos Aq Mt sin@2f30.org , Err bitreich.org 70 1diff --git a/dup-pack.c b/dup-pack.c /scm/dedup/file/dup-pack.c.gph bitreich.org 70 i@@ -1,202 +1,73 @@ Err bitreich.org 70 i #include Err bitreich.org 70 i #include Err bitreich.org 70 i-#include Err bitreich.org 70 i Err bitreich.org 70 i #include Err bitreich.org 70 i #include Err bitreich.org 70 i+#include Err bitreich.org 70 i #include Err bitreich.org 70 i-#include Err bitreich.org 70 i #include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i Err bitreich.org 70 i #include "arg.h" Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-static struct snap_hdr snap_hdr; Err bitreich.org 70 i-static struct blk_hdr blk_hdr; Err bitreich.org 70 i-static struct icache *icache; Err bitreich.org 70 i-static int ifd; Err bitreich.org 70 i-static int sfd; Err bitreich.org 70 i-static int hash_algo = HASH_BLAKE2B; Err bitreich.org 70 i-static int compr_algo = COMPR_LZ4; Err bitreich.org 70 i+#include "block.h" Err bitreich.org 70 i+#include "chunker.h" Err bitreich.org 70 i+#include "config.h" Err bitreich.org 70 i+#include "snap.h" Err bitreich.org 70 i Err bitreich.org 70 i int verbose; Err bitreich.org 70 i char *argv0; Err bitreich.org 70 i Err bitreich.org 70 i-static void Err bitreich.org 70 i-dedup_chunk(struct snap *snap, uint8_t *chunkp, size_t chunk_size) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t md[MD_SIZE]; Err bitreich.org 70 i- struct blk_desc blk_desc; Err bitreich.org 70 i- struct compr_ctx ctx; Err bitreich.org 70 i- uint8_t *compr_buf; Err bitreich.org 70 i- size_t n, csize; Err bitreich.org 70 i- Err bitreich.org 70 i- if (compr_init(&ctx, compr_algo) < 0) Err bitreich.org 70 i- errx(1, "compr_init failed"); Err bitreich.org 70 i- csize = compr_size(&ctx, BLKSIZE_MAX); Err bitreich.org 70 i- compr_buf = alloc_buf(csize); Err bitreich.org 70 i- Err bitreich.org 70 i- n = compr(&ctx, chunkp, compr_buf, chunk_size, csize); Err bitreich.org 70 i- hash_blk(compr_buf, n, md, hash_algo); Err bitreich.org 70 i- Err bitreich.org 70 i- snap_hdr.st.orig_size += chunk_size; Err bitreich.org 70 i- snap_hdr.st.compr_size += n; Err bitreich.org 70 i- Err bitreich.org 70 i- memcpy(blk_desc.md, md, sizeof(blk_desc.md)); Err bitreich.org 70 i- if (lookup_icache(icache, &blk_desc) < 0) { Err bitreich.org 70 i- blk_desc.offset = blk_hdr.size; Err bitreich.org 70 i- blk_desc.size = n; Err bitreich.org 70 i- Err bitreich.org 70 i- snap->blk_desc[snap->nr_blk_descs++] = blk_desc; Err bitreich.org 70 i- append_blk(sfd, &blk_hdr, compr_buf, &blk_desc); Err bitreich.org 70 i- Err bitreich.org 70 i- insert_icache(icache, &blk_desc); Err bitreich.org 70 i- Err bitreich.org 70 i- snap_hdr.st.dedup_size += blk_desc.size; Err bitreich.org 70 i- snap_hdr.st.nr_blks++; Err bitreich.org 70 i- Err bitreich.org 70 i- if (blk_desc.size > snap_hdr.st.max_blk_size) Err bitreich.org 70 i- snap_hdr.st.max_blk_size = blk_desc.size; Err bitreich.org 70 i- if (blk_desc.size < snap_hdr.st.min_blk_size) Err bitreich.org 70 i- snap_hdr.st.min_blk_size = blk_desc.size; Err bitreich.org 70 i- } else { Err bitreich.org 70 i- snap->blk_desc[snap->nr_blk_descs++] = blk_desc; Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- free(compr_buf); Err bitreich.org 70 i- compr_final(&ctx); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-dedup(int fd, char *msg) Err bitreich.org 70 i+static int Err bitreich.org 70 i+pack(struct sctx *sctx, struct bctx *bctx) Err bitreich.org 70 i { Err bitreich.org 70 i- struct snap *snap; Err bitreich.org 70 i- struct chunker *chunker; Err bitreich.org 70 i+ struct chunker *c; Err bitreich.org 70 i Err bitreich.org 70 i- snap = alloc_snap(); Err bitreich.org 70 i- chunker = alloc_chunker(fd, BLKSIZE_MIN, BLKSIZE_MAX, Err bitreich.org 70 i- HASHMASK_BITS, WINSIZE); Err bitreich.org 70 i+ if ((c = copen(0, BSIZEMIN, BSIZEMAX, HMASKBITS, WINSIZE)) == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i Err bitreich.org 70 i- while (fill_chunker(chunker) > 0) { Err bitreich.org 70 i- uint8_t *chunkp; Err bitreich.org 70 i- size_t chunk_size; Err bitreich.org 70 i- Err bitreich.org 70 i- chunkp = get_chunk(chunker, &chunk_size); Err bitreich.org 70 i- snap = grow_snap(snap, snap->nr_blk_descs + 1); Err bitreich.org 70 i- dedup_chunk(snap, chunkp, chunk_size); Err bitreich.org 70 i- drain_chunker(chunker); Err bitreich.org 70 i- } Err bitreich.org 70 i+ while (cfill(c) > 0) { Err bitreich.org 70 i+ unsigned char md[MDSIZE]; Err bitreich.org 70 i+ void *buf; Err bitreich.org 70 i+ size_t n; Err bitreich.org 70 i Err bitreich.org 70 i- if (snap->nr_blk_descs > 0) { Err bitreich.org 70 i- if (msg != NULL) { Err bitreich.org 70 i- size_t size; Err bitreich.org 70 i- Err bitreich.org 70 i- size = strlen(msg) + 1; Err bitreich.org 70 i- if (size > sizeof(snap->msg)) Err bitreich.org 70 i- size = sizeof(snap->msg); Err bitreich.org 70 i- memcpy(snap->msg, msg, size); Err bitreich.org 70 i- snap->msg[size - 1] = '\0'; Err bitreich.org 70 i+ buf = cget(c, &n); Err bitreich.org 70 i+ if (bput(bctx, buf, n, md) < 0) { Err bitreich.org 70 i+ cclose(c); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i } Err bitreich.org 70 i- hash_snap(snap, snap->md, hash_algo); Err bitreich.org 70 i- append_snap(ifd, &snap_hdr, snap); Err bitreich.org 70 i- Err bitreich.org 70 i- if (verbose > 0) { Err bitreich.org 70 i- unsigned long long hits, misses; Err bitreich.org 70 i- double hitratio; Err bitreich.org 70 i Err bitreich.org 70 i- icache_stats(icache, &hits, &misses); Err bitreich.org 70 i- hitratio = (double)hits / (hits + misses); Err bitreich.org 70 i- fprintf(stderr, "Index cache hit percentage: %.2f%%\n", Err bitreich.org 70 i- 100 * hitratio); Err bitreich.org 70 i+ if (sput(sctx, md) < 0) { Err bitreich.org 70 i+ cclose(c); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i } Err bitreich.org 70 i- } Err bitreich.org 70 i- Err bitreich.org 70 i- free_chunker(chunker); Err bitreich.org 70 i- free_snap(snap); Err bitreich.org 70 i-} Err bitreich.org 70 i Err bitreich.org 70 i-static int Err bitreich.org 70 i-build_icache(struct snap *snap, void *arg) Err bitreich.org 70 i-{ Err bitreich.org 70 i- struct compr_ctx ctx; Err bitreich.org 70 i- uint8_t *buf; Err bitreich.org 70 i- uint64_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if (compr_init(&ctx, compr_algo) < 0) Err bitreich.org 70 i- errx(1, "compr_init failed"); Err bitreich.org 70 i- buf = alloc_buf(compr_size(&ctx, BLKSIZE_MAX)); Err bitreich.org 70 i- for (i = 0; i < snap->nr_blk_descs; i++) { Err bitreich.org 70 i- struct blk_desc *blk_desc; Err bitreich.org 70 i- Err bitreich.org 70 i- blk_desc = &snap->blk_desc[i]; Err bitreich.org 70 i- insert_icache(icache, blk_desc); Err bitreich.org 70 i+ if (cdrain(c) < 0) { Err bitreich.org 70 i+ cclose(c); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i } Err bitreich.org 70 i- free(buf); Err bitreich.org 70 i- compr_final(&ctx); Err bitreich.org 70 i- return WALK_CONTINUE; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-init(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- ifd = open(SNAPSF, O_RDWR, 0600); Err bitreich.org 70 i- if (ifd < 0) Err bitreich.org 70 i- err(1, "open %s", SNAPSF); Err bitreich.org 70 i- Err bitreich.org 70 i- sfd = open(STOREF, O_RDWR, 0600); Err bitreich.org 70 i- if (sfd < 0) Err bitreich.org 70 i- err(1, "open %s", STOREF); Err bitreich.org 70 i- Err bitreich.org 70 i- if (flock(ifd, LOCK_NB | LOCK_EX) < 0 || Err bitreich.org 70 i- flock(sfd, LOCK_NB | LOCK_EX) < 0) Err bitreich.org 70 i- err(1, "flock"); Err bitreich.org 70 i- Err bitreich.org 70 i- Err bitreich.org 70 i- xlseek(ifd, 0, SEEK_SET); Err bitreich.org 70 i- load_snap_hdr(ifd, &snap_hdr); Err bitreich.org 70 i- xlseek(sfd, 0, SEEK_SET); Err bitreich.org 70 i- load_blk_hdr(sfd, &blk_hdr, &compr_algo, &hash_algo); Err bitreich.org 70 i- Err bitreich.org 70 i- icache = alloc_icache(); Err bitreich.org 70 i- walk_snap(ifd, &snap_hdr, build_icache, NULL); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-term(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- xlseek(ifd, 0, SEEK_SET); Err bitreich.org 70 i- write_snap_hdr(ifd, &snap_hdr); Err bitreich.org 70 i- xlseek(sfd, 0, SEEK_SET); Err bitreich.org 70 i- write_blk_hdr(sfd, &blk_hdr); Err bitreich.org 70 i- Err bitreich.org 70 i- fsync(ifd); Err bitreich.org 70 i- fsync(sfd); Err bitreich.org 70 i- Err bitreich.org 70 i- close(ifd); Err bitreich.org 70 i- close(sfd); Err bitreich.org 70 i- Err bitreich.org 70 i- free_icache(icache); Err bitreich.org 70 i+ return cclose(c); Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i static void Err bitreich.org 70 i usage(void) Err bitreich.org 70 i { Err bitreich.org 70 i- fprintf(stderr, "usage: %s [-v] [-m message] [repo]\n", argv0); Err bitreich.org 70 i+ fprintf(stderr, "usage: %s [-v] [-r repo] name\n", argv0); Err bitreich.org 70 i exit(1); Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i int Err bitreich.org 70 i main(int argc, char *argv[]) Err bitreich.org 70 i { Err bitreich.org 70 i- char *repo, *msg = NULL; Err bitreich.org 70 i+ char path[PATH_MAX]; Err bitreich.org 70 i+ struct sctx *sctx; Err bitreich.org 70 i+ struct bctx *bctx; Err bitreich.org 70 i+ struct bparam bparam; Err bitreich.org 70 i+ char *repo = "."; Err bitreich.org 70 i Err bitreich.org 70 i ARGBEGIN { Err bitreich.org 70 i- case 'm': Err bitreich.org 70 i- msg = EARGF(usage()); Err bitreich.org 70 i- break; Err bitreich.org 70 i+ case 'r': Err bitreich.org 70 i+ repo = EARGF(usage()); Err bitreich.org 70 i+ break; Err bitreich.org 70 i case 'v': Err bitreich.org 70 i verbose++; Err bitreich.org 70 i break; Err bitreich.org 70 i@@ -204,22 +75,23 @@ main(int argc, char *argv[]) Err bitreich.org 70 i usage(); Err bitreich.org 70 i } ARGEND Err bitreich.org 70 i Err bitreich.org 70 i- switch (argc) { Err bitreich.org 70 i- case 0: Err bitreich.org 70 i- repo = "."; Err bitreich.org 70 i- break; Err bitreich.org 70 i- case 1: Err bitreich.org 70 i- repo = argv[0]; Err bitreich.org 70 i- break; Err bitreich.org 70 i- default: Err bitreich.org 70 i+ if (argc != 1) Err bitreich.org 70 i usage(); Err bitreich.org 70 i- }; Err bitreich.org 70 i Err bitreich.org 70 i- if (chdir(repo) < 0) Err bitreich.org 70 i- err(1, "chdir: %s", repo); Err bitreich.org 70 i+ snprintf(path, sizeof(path), "%s/archive/%s", repo, argv[0]); Err bitreich.org 70 i+ if (screat(path, 0600, &sctx) < 0) Err bitreich.org 70 i+ errx(1, "screat: %s: failed", path); Err bitreich.org 70 i+ Err bitreich.org 70 i+ snprintf(path, sizeof(path), "%s/storage", repo); Err bitreich.org 70 i+ if (bopen(path, O_RDWR, 0600, &bparam, &bctx) <0) Err bitreich.org 70 i+ errx(1, "bopen: %s: failed", path); Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (pack(sctx, bctx) < 0) Err bitreich.org 70 i+ errx(1, "pack: failed"); Err bitreich.org 70 i Err bitreich.org 70 i- init(); Err bitreich.org 70 i- dedup(STDIN_FILENO, msg); Err bitreich.org 70 i- term(); Err bitreich.org 70 i+ if (bclose(bctx) < 0) Err bitreich.org 70 i+ errx(1, "bclose: failed"); Err bitreich.org 70 i+ if (sclose(sctx) < 0) Err bitreich.org 70 i+ errx(1, "sclose: failed"); Err bitreich.org 70 i return 0; Err bitreich.org 70 i } Err bitreich.org 70 1diff --git a/dup-unpack.1 b/dup-unpack.1 /scm/dedup/file/dup-unpack.1.gph bitreich.org 70 i@@ -1,4 +1,4 @@ Err bitreich.org 70 i-.Dd April 18, 2019 Err bitreich.org 70 i+.Dd April 25, 2019 Err bitreich.org 70 i .Dt DUP-UNPACK 1 Err bitreich.org 70 i .Os Err bitreich.org 70 i .Sh NAME Err bitreich.org 70 i@@ -7,19 +7,18 @@ Err bitreich.org 70 i .Sh SYNOPSIS Err bitreich.org 70 i .Nm dup-unpack Err bitreich.org 70 i .Op Fl v Err bitreich.org 70 i-.Ar id Err bitreich.org 70 i-.Op repo Err bitreich.org 70 i+.Op Fl r Ar repo Err bitreich.org 70 i+.Ar name Err bitreich.org 70 i .Sh DESCRIPTION Err bitreich.org 70 i .Nm Err bitreich.org 70 i extracts the snapshot specified by Err bitreich.org 70 i-.Ar id Err bitreich.org 70 i+.Ar name Err bitreich.org 70 i from the dedup repository and writes the data to stdout. Err bitreich.org 70 i-If no Err bitreich.org 70 i-.Ar repo Err bitreich.org 70 i-is specified, then the current directory Err bitreich.org 70 i-is assumed to be the repository. Err bitreich.org 70 i .Sh OPTIONS Err bitreich.org 70 i-.Bl -tag -width "-v" Err bitreich.org 70 i+.Bl -tag -width "-r repo" Err bitreich.org 70 i+.It Fl r Ar repo Err bitreich.org 70 i+Set repository directory. Err bitreich.org 70 i+By default the current working directory is used. Err bitreich.org 70 i .It Fl v Err bitreich.org 70 i Enable verbose mode. Err bitreich.org 70 i .El Err bitreich.org 70 1diff --git a/dup-unpack.c b/dup-unpack.c /scm/dedup/file/dup-unpack.c.gph bitreich.org 70 i@@ -1,109 +1,89 @@ Err bitreich.org 70 i #include Err bitreich.org 70 i #include Err bitreich.org 70 i-#include Err bitreich.org 70 i Err bitreich.org 70 i #include Err bitreich.org 70 i #include Err bitreich.org 70 i+#include Err bitreich.org 70 i #include Err bitreich.org 70 i-#include Err bitreich.org 70 i #include Err bitreich.org 70 i-#include Err bitreich.org 70 i #include Err bitreich.org 70 i Err bitreich.org 70 i #include "arg.h" Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-struct extract_args { Err bitreich.org 70 i- uint8_t *md; Err bitreich.org 70 i- int fd; Err bitreich.org 70 i- int ret; Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-static struct snap_hdr snap_hdr; Err bitreich.org 70 i-static struct blk_hdr blk_hdr; Err bitreich.org 70 i-static int ifd; Err bitreich.org 70 i-static int sfd; Err bitreich.org 70 i-static int hash_algo = HASH_BLAKE2B; Err bitreich.org 70 i-static int compr_algo = COMPR_LZ4; Err bitreich.org 70 i+#include "block.h" Err bitreich.org 70 i+#include "config.h" Err bitreich.org 70 i+#include "snap.h" Err bitreich.org 70 i Err bitreich.org 70 i int verbose; Err bitreich.org 70 i char *argv0; Err bitreich.org 70 i Err bitreich.org 70 i-static int Err bitreich.org 70 i-extract(struct snap *snap, void *arg) Err bitreich.org 70 i+static ssize_t Err bitreich.org 70 i+xwrite(int fd, void *buf, size_t nbytes) Err bitreich.org 70 i { Err bitreich.org 70 i- uint8_t *buf[2]; Err bitreich.org 70 i- struct extract_args *args = arg; Err bitreich.org 70 i- struct compr_ctx ctx; Err bitreich.org 70 i- uint64_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if (memcmp(snap->md, args->md, sizeof(snap->md)) != 0) Err bitreich.org 70 i- return WALK_CONTINUE; Err bitreich.org 70 i- Err bitreich.org 70 i- if (compr_init(&ctx, compr_algo) < 0) Err bitreich.org 70 i- errx(1, "compr_init failed"); Err bitreich.org 70 i- buf[0] = alloc_buf(BLKSIZE_MAX); Err bitreich.org 70 i- buf[1] = alloc_buf(compr_size(&ctx, BLKSIZE_MAX)); Err bitreich.org 70 i- for (i = 0; i < snap->nr_blk_descs; i++) { Err bitreich.org 70 i- struct blk_desc *blk_desc; Err bitreich.org 70 i- size_t blksize; Err bitreich.org 70 i- Err bitreich.org 70 i- blk_desc = &snap->blk_desc[i]; Err bitreich.org 70 i- read_blk(sfd, buf[1], blk_desc); Err bitreich.org 70 i- blksize = decompr(&ctx, buf[1], buf[0], blk_desc->size, BLKSIZE_MAX); Err bitreich.org 70 i- xwrite(args->fd, buf[0], blksize); Err bitreich.org 70 i+ unsigned char *bp = buf; Err bitreich.org 70 i+ ssize_t total = 0; Err bitreich.org 70 i+ Err bitreich.org 70 i+ while (nbytes > 0) { Err bitreich.org 70 i+ ssize_t n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ n = write(fd, &bp[total], nbytes); Err bitreich.org 70 i+ if (n < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ else if (n == 0) Err bitreich.org 70 i+ return total; Err bitreich.org 70 i+ total += n; Err bitreich.org 70 i+ nbytes -= n; Err bitreich.org 70 i } Err bitreich.org 70 i- free_buf(buf[1]); Err bitreich.org 70 i- free_buf(buf[0]); Err bitreich.org 70 i- compr_final(&ctx); Err bitreich.org 70 i- args->ret = 0; Err bitreich.org 70 i- return WALK_STOP; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-init(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- ifd = open(SNAPSF, O_RDONLY, 0600); Err bitreich.org 70 i- if (ifd < 0) Err bitreich.org 70 i- err(1, "open %s", SNAPSF); Err bitreich.org 70 i- Err bitreich.org 70 i- sfd = open(STOREF, O_RDONLY, 0600); Err bitreich.org 70 i- if (sfd < 0) Err bitreich.org 70 i- err(1, "open %s", STOREF); Err bitreich.org 70 i- Err bitreich.org 70 i- if (flock(ifd, LOCK_NB | LOCK_EX) < 0 || Err bitreich.org 70 i- flock(sfd, LOCK_NB | LOCK_EX) < 0) Err bitreich.org 70 i- err(1, "flock"); Err bitreich.org 70 i- Err bitreich.org 70 i- xlseek(ifd, 0, SEEK_SET); Err bitreich.org 70 i- load_snap_hdr(ifd, &snap_hdr); Err bitreich.org 70 i- xlseek(sfd, 0, SEEK_SET); Err bitreich.org 70 i- load_blk_hdr(sfd, &blk_hdr, &compr_algo, &hash_algo); Err bitreich.org 70 i+ return total; Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i-static void Err bitreich.org 70 i-term(void) Err bitreich.org 70 i+static int Err bitreich.org 70 i+unpack(struct sctx *sctx, struct bctx *bctx) Err bitreich.org 70 i { Err bitreich.org 70 i- close(ifd); Err bitreich.org 70 i- close(sfd); Err bitreich.org 70 i+ unsigned char md[MDSIZE]; Err bitreich.org 70 i+ void *buf; Err bitreich.org 70 i+ int sn; Err bitreich.org 70 i+ Err bitreich.org 70 i+ buf = malloc(BSIZEMAX); Err bitreich.org 70 i+ if (buf == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ while ((sn = sget(sctx, md)) == MDSIZE) { Err bitreich.org 70 i+ size_t n = BSIZEMAX; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (bget(bctx, md, buf, &n) < 0) { Err bitreich.org 70 i+ free(buf); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ if (xwrite(1, buf, n) != n) { Err bitreich.org 70 i+ free(buf); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ } Err bitreich.org 70 i+ free(buf); Err bitreich.org 70 i+ if (sn < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i static void Err bitreich.org 70 i usage(void) Err bitreich.org 70 i { Err bitreich.org 70 i- fprintf(stderr, "usage: %s [-v] id [repo]\n", argv0); Err bitreich.org 70 i+ fprintf(stderr, "usage: %s [-v] [-r repo] name\n", argv0); Err bitreich.org 70 i exit(1); Err bitreich.org 70 i } Err bitreich.org 70 i Err bitreich.org 70 i int Err bitreich.org 70 i main(int argc, char *argv[]) Err bitreich.org 70 i { Err bitreich.org 70 i- uint8_t md[MD_SIZE]; Err bitreich.org 70 i- char *repo, *id = NULL; Err bitreich.org 70 i- struct extract_args args; Err bitreich.org 70 i+ char path[PATH_MAX]; Err bitreich.org 70 i+ struct sctx *sctx; Err bitreich.org 70 i+ struct bctx *bctx; Err bitreich.org 70 i+ struct bparam bparam; Err bitreich.org 70 i+ char *repo = "."; Err bitreich.org 70 i Err bitreich.org 70 i ARGBEGIN { Err bitreich.org 70 i+ case 'r': Err bitreich.org 70 i+ repo = EARGF(usage()); Err bitreich.org 70 i+ break; Err bitreich.org 70 i case 'v': Err bitreich.org 70 i verbose++; Err bitreich.org 70 i break; Err bitreich.org 70 i@@ -111,30 +91,24 @@ main(int argc, char *argv[]) Err bitreich.org 70 i usage(); Err bitreich.org 70 i } ARGEND Err bitreich.org 70 i Err bitreich.org 70 i- switch (argc) { Err bitreich.org 70 i- case 1: Err bitreich.org 70 i- id = argv[0]; Err bitreich.org 70 i- repo = "."; Err bitreich.org 70 i- break; Err bitreich.org 70 i- case 2: Err bitreich.org 70 i- id = argv[0]; Err bitreich.org 70 i- repo = argv[1]; Err bitreich.org 70 i- break; Err bitreich.org 70 i- default: Err bitreich.org 70 i+ if (argc != 1) Err bitreich.org 70 i usage(); Err bitreich.org 70 i- }; Err bitreich.org 70 i- Err bitreich.org 70 i- if (chdir(repo) < 0) Err bitreich.org 70 i- err(1, "chdir: %s", repo); Err bitreich.org 70 i- Err bitreich.org 70 i- init(); Err bitreich.org 70 i- str2bin(id, md); Err bitreich.org 70 i- args.md = md; Err bitreich.org 70 i- args.fd = STDOUT_FILENO; Err bitreich.org 70 i- args.ret = -1; Err bitreich.org 70 i- walk_snap(ifd, &snap_hdr, extract, &args); Err bitreich.org 70 i- if (args.ret != 0) Err bitreich.org 70 i- errx(1, "unknown snapshot: %s", id); Err bitreich.org 70 i- term(); Err bitreich.org 70 i+ Err bitreich.org 70 i+ snprintf(path, sizeof(path), "%s/archive/%s", repo, argv[0]); Err bitreich.org 70 i+ if (sopen(path, O_RDONLY, 0600, &sctx) < 0) Err bitreich.org 70 i+ errx(1, "sopen: %s: failed", path); Err bitreich.org 70 i+ Err bitreich.org 70 i+ snprintf(path, sizeof(path), "%s/storage", repo); Err bitreich.org 70 i+ if (bopen(path, O_RDONLY, 0600, &bparam, &bctx) <0) Err bitreich.org 70 i+ errx(1, "bopen: %s: failed", path); Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (unpack(sctx, bctx) < 0) Err bitreich.org 70 i+ errx(1, "dedup: failed"); Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (bclose(bctx) < 0) Err bitreich.org 70 i+ errx(1, "bclose: failed"); Err bitreich.org 70 i+ if (sclose(sctx) < 0) Err bitreich.org 70 i+ errx(1, "sclose: failed"); Err bitreich.org 70 i+ Err bitreich.org 70 i return 0; Err bitreich.org 70 i } Err bitreich.org 70 1diff --git a/hash-blake2b.c b/hash-blake2b.c /scm/dedup/file/hash-blake2b.c.gph bitreich.org 70 i@@ -1,26 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2bi(struct hash_ctx *ctx, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2b_init(&ctx->u.blake2b_ctx, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2bu(struct hash_ctx *ctx, const void *buf, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2b_update(&ctx->u.blake2b_ctx, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2bf(struct hash_ctx *ctx, void *buf, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2b_final(&ctx->u.blake2b_ctx, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/hash-blake2bp.c b/hash-blake2bp.c /scm/dedup/file/hash-blake2bp.c.gph bitreich.org 70 i@@ -1,26 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2bpi(struct hash_ctx *ctx, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2bp_init(&ctx->u.blake2bp_ctx, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2bpu(struct hash_ctx *ctx, const void *buf, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2bp_update(&ctx->u.blake2bp_ctx, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2bpf(struct hash_ctx *ctx, void *buf, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2bp_final(&ctx->u.blake2bp_ctx, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/hash-blake2s.c b/hash-blake2s.c /scm/dedup/file/hash-blake2s.c.gph bitreich.org 70 i@@ -1,26 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2si(struct hash_ctx *ctx, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2s_init(&ctx->u.blake2s_ctx, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2su(struct hash_ctx *ctx, const void *buf, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2s_update(&ctx->u.blake2s_ctx, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2sf(struct hash_ctx *ctx, void *buf, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2s_final(&ctx->u.blake2s_ctx, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/hash-blake2sp.c b/hash-blake2sp.c /scm/dedup/file/hash-blake2sp.c.gph bitreich.org 70 i@@ -1,26 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2spi(struct hash_ctx *ctx, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2sp_init(&ctx->u.blake2sp_ctx, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2spu(struct hash_ctx *ctx, const void *buf, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2sp_update(&ctx->u.blake2sp_ctx, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-blake2spf(struct hash_ctx *ctx, void *buf, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return blake2sp_final(&ctx->u.blake2sp_ctx, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/hash.c b/hash.c /scm/dedup/file/hash.c.gph bitreich.org 70 i@@ -1,94 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-static struct hash_ops { Err bitreich.org 70 i- int (*init)(struct hash_ctx *ctx, size_t n); Err bitreich.org 70 i- int (*update)(struct hash_ctx *ctx, const void *buf, size_t n); Err bitreich.org 70 i- int (*final)(struct hash_ctx *ctx, void *buf, size_t n); Err bitreich.org 70 i-} hashes[NR_HASHES] = { Err bitreich.org 70 i- { Err bitreich.org 70 i- .init = blake2bi, Err bitreich.org 70 i- .update = blake2bu, Err bitreich.org 70 i- .final = blake2bf, Err bitreich.org 70 i- }, Err bitreich.org 70 i- { Err bitreich.org 70 i- .init = blake2bpi, Err bitreich.org 70 i- .update = blake2bpu, Err bitreich.org 70 i- .final = blake2bpf, Err bitreich.org 70 i- }, Err bitreich.org 70 i- { Err bitreich.org 70 i- .init = blake2si, Err bitreich.org 70 i- .update = blake2su, Err bitreich.org 70 i- .final = blake2sf, Err bitreich.org 70 i- }, Err bitreich.org 70 i- { Err bitreich.org 70 i- .init = blake2spi, Err bitreich.org 70 i- .update = blake2spu, Err bitreich.org 70 i- .final = blake2spf, Err bitreich.org 70 i- }, Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-static char *algomap[NR_HASHES] = { Err bitreich.org 70 i- [HASH_BLAKE2B] = "blake2b", Err bitreich.org 70 i- [HASH_BLAKE2BP] = "blake2bp", Err bitreich.org 70 i- [HASH_BLAKE2S] = "blake2s", Err bitreich.org 70 i- [HASH_BLAKE2SP] = "blake2sp", Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-hash_init(struct hash_ctx *ctx, int type, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- if (type < 0 || type >= NR_HASHES) Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- Err bitreich.org 70 i- ctx->ops = &hashes[type]; Err bitreich.org 70 i- return (*ctx->ops->init)(ctx, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-hash_update(struct hash_ctx *ctx, const void *buf, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return (*ctx->ops->update)(ctx, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-hash_final(struct hash_ctx *ctx, void *buf, size_t n) Err bitreich.org 70 i-{ Err bitreich.org 70 i- return (*ctx->ops->final)(ctx, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-hash_name2type(char *name) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- for (i = 0; i < NR_HASHES; i++) Err bitreich.org 70 i- if (strcasecmp(algomap[i], name) == 0) Err bitreich.org 70 i- return i; Err bitreich.org 70 i- return -1; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-char * Err bitreich.org 70 i-hash_type2name(int type) Err bitreich.org 70 i-{ Err bitreich.org 70 i- if (type < 0 || type >= NR_HASHES) Err bitreich.org 70 i- return NULL; Err bitreich.org 70 i- return algomap[type]; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-hash_list(int fd) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- for (i = 0; i < NR_HASHES; i++) Err bitreich.org 70 i- dprintf(fd, "%s\n", algomap[i]); Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/icache.c b/icache.c /scm/dedup/file/icache.c.gph bitreich.org 70 i@@ -1,114 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i-#include "tree.h" Err bitreich.org 70 i- Err bitreich.org 70 i-struct node { Err bitreich.org 70 i- struct blk_desc desc; Err bitreich.org 70 i- RB_ENTRY(node) e; Err bitreich.org 70 i-}; Err bitreich.org 70 i-RB_HEAD(icache_head, node); Err bitreich.org 70 i- Err bitreich.org 70 i-struct icache { Err bitreich.org 70 i- struct icache_head nodes; Err bitreich.org 70 i- unsigned long long hits; Err bitreich.org 70 i- unsigned long long misses; Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-static int Err bitreich.org 70 i-node_cmp(struct node *e1, struct node *e2) Err bitreich.org 70 i-{ Err bitreich.org 70 i- int r; Err bitreich.org 70 i- Err bitreich.org 70 i- r = memcmp(e1->desc.md, e2->desc.md, sizeof(e1->desc.md)); Err bitreich.org 70 i- if (r > 0) Err bitreich.org 70 i- return 1; Err bitreich.org 70 i- else if (r < 0) Err bitreich.org 70 i- return -1; Err bitreich.org 70 i- return 0; Err bitreich.org 70 i-} Err bitreich.org 70 i-static RB_PROTOTYPE(icache_head, node, e, node_cmp); Err bitreich.org 70 i-static RB_GENERATE(icache_head, node, e, node_cmp); Err bitreich.org 70 i- Err bitreich.org 70 i-static struct node * Err bitreich.org 70 i-alloc_node(struct blk_desc *desc) Err bitreich.org 70 i-{ Err bitreich.org 70 i- struct node *node; Err bitreich.org 70 i- Err bitreich.org 70 i- node = calloc(1, sizeof(*node)); Err bitreich.org 70 i- if (node == NULL) Err bitreich.org 70 i- err(1, "calloc"); Err bitreich.org 70 i- node->desc = *desc; Err bitreich.org 70 i- return node; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-free_node(struct node *node) Err bitreich.org 70 i-{ Err bitreich.org 70 i- free(node); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-struct icache * Err bitreich.org 70 i-alloc_icache(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- struct icache *icache; Err bitreich.org 70 i- Err bitreich.org 70 i- icache = calloc(1, sizeof(*icache)); Err bitreich.org 70 i- if (icache == NULL) Err bitreich.org 70 i- err(1, "calloc"); Err bitreich.org 70 i- RB_INIT(&icache->nodes); Err bitreich.org 70 i- return icache; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-free_icache(struct icache *icache) Err bitreich.org 70 i-{ Err bitreich.org 70 i- struct node *node, *tmp; Err bitreich.org 70 i- Err bitreich.org 70 i- RB_FOREACH_SAFE(node, icache_head, &icache->nodes, tmp) { Err bitreich.org 70 i- RB_REMOVE(icache_head, &icache->nodes, node); Err bitreich.org 70 i- free_node(node); Err bitreich.org 70 i- } Err bitreich.org 70 i- free(icache); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-insert_icache(struct icache *icache, struct blk_desc *desc) Err bitreich.org 70 i-{ Err bitreich.org 70 i- struct node *node; Err bitreich.org 70 i- Err bitreich.org 70 i- node = alloc_node(desc); Err bitreich.org 70 i- if (RB_INSERT(icache_head, &icache->nodes, node) != NULL) Err bitreich.org 70 i- free_node(node); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-int Err bitreich.org 70 i-lookup_icache(struct icache *icache, struct blk_desc *desc) Err bitreich.org 70 i-{ Err bitreich.org 70 i- struct node *node, key; Err bitreich.org 70 i- Err bitreich.org 70 i- key.desc = *desc; Err bitreich.org 70 i- node = RB_FIND(icache_head, &icache->nodes, &key); Err bitreich.org 70 i- if (node != NULL) { Err bitreich.org 70 i- icache->hits++; Err bitreich.org 70 i- *desc = node->desc; Err bitreich.org 70 i- return 0; Err bitreich.org 70 i- } Err bitreich.org 70 i- icache->misses++; Err bitreich.org 70 i- return -1; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-icache_stats(struct icache *icache, unsigned long long *hits, Err bitreich.org 70 i- unsigned long long *misses) Err bitreich.org 70 i-{ Err bitreich.org 70 i- *hits = icache->hits; Err bitreich.org 70 i- *misses = icache->misses; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 1diff --git a/queue.h b/queue.h /scm/dedup/file/queue.h.gph bitreich.org 70 i@@ -0,0 +1,534 @@ Err bitreich.org 70 i+/* $OpenBSD: queue.h,v 1.45 2018/07/12 14:22:54 sashan Exp $ */ Err bitreich.org 70 i+/* $NetBSD: queue.h,v 1.11 1996/05/16 05:17:14 mycroft Exp $ */ Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * Copyright (c) 1991, 1993 Err bitreich.org 70 i+ * The Regents of the University of California. All rights reserved. Err bitreich.org 70 i+ * Err bitreich.org 70 i+ * Redistribution and use in source and binary forms, with or without Err bitreich.org 70 i+ * modification, are permitted provided that the following conditions Err bitreich.org 70 i+ * are met: Err bitreich.org 70 i+ * 1. Redistributions of source code must retain the above copyright Err bitreich.org 70 i+ * notice, this list of conditions and the following disclaimer. Err bitreich.org 70 i+ * 2. Redistributions in binary form must reproduce the above copyright Err bitreich.org 70 i+ * notice, this list of conditions and the following disclaimer in the Err bitreich.org 70 i+ * documentation and/or other materials provided with the distribution. Err bitreich.org 70 i+ * 3. Neither the name of the University nor the names of its contributors Err bitreich.org 70 i+ * may be used to endorse or promote products derived from this software Err bitreich.org 70 i+ * without specific prior written permission. Err bitreich.org 70 i+ * Err bitreich.org 70 i+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND Err bitreich.org 70 i+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE Err bitreich.org 70 i+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE Err bitreich.org 70 i+ * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE Err bitreich.org 70 i+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL Err bitreich.org 70 i+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS Err bitreich.org 70 i+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) Err bitreich.org 70 i+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT Err bitreich.org 70 i+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY Err bitreich.org 70 i+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF Err bitreich.org 70 i+ * SUCH DAMAGE. Err bitreich.org 70 i+ * Err bitreich.org 70 i+ * @(#)queue.h 8.5 (Berkeley) 8/20/94 Err bitreich.org 70 i+ */ Err bitreich.org 70 i+ Err bitreich.org 70 i+#ifndef _SYS_QUEUE_H_ Err bitreich.org 70 i+#define _SYS_QUEUE_H_ Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * This file defines five types of data structures: singly-linked lists, Err bitreich.org 70 i+ * lists, simple queues, tail queues and XOR simple queues. Err bitreich.org 70 i+ * Err bitreich.org 70 i+ * Err bitreich.org 70 i+ * A singly-linked list is headed by a single forward pointer. The elements Err bitreich.org 70 i+ * are singly linked for minimum space and pointer manipulation overhead at Err bitreich.org 70 i+ * the expense of O(n) removal for arbitrary elements. New elements can be Err bitreich.org 70 i+ * added to the list after an existing element or at the head of the list. Err bitreich.org 70 i+ * Elements being removed from the head of the list should use the explicit Err bitreich.org 70 i+ * macro for this purpose for optimum efficiency. A singly-linked list may Err bitreich.org 70 i+ * only be traversed in the forward direction. Singly-linked lists are ideal Err bitreich.org 70 i+ * for applications with large datasets and few or no removals or for Err bitreich.org 70 i+ * implementing a LIFO queue. Err bitreich.org 70 i+ * Err bitreich.org 70 i+ * A list is headed by a single forward pointer (or an array of forward Err bitreich.org 70 i+ * pointers for a hash table header). The elements are doubly linked Err bitreich.org 70 i+ * so that an arbitrary element can be removed without a need to Err bitreich.org 70 i+ * traverse the list. New elements can be added to the list before Err bitreich.org 70 i+ * or after an existing element or at the head of the list. A list Err bitreich.org 70 i+ * may only be traversed in the forward direction. Err bitreich.org 70 i+ * Err bitreich.org 70 i+ * A simple queue is headed by a pair of pointers, one to the head of the Err bitreich.org 70 i+ * list and the other to the tail of the list. The elements are singly Err bitreich.org 70 i+ * linked to save space, so elements can only be removed from the Err bitreich.org 70 i+ * head of the list. New elements can be added to the list before or after Err bitreich.org 70 i+ * an existing element, at the head of the list, or at the end of the Err bitreich.org 70 i+ * list. A simple queue may only be traversed in the forward direction. Err bitreich.org 70 i+ * Err bitreich.org 70 i+ * A tail queue is headed by a pair of pointers, one to the head of the Err bitreich.org 70 i+ * list and the other to the tail of the list. The elements are doubly Err bitreich.org 70 i+ * linked so that an arbitrary element can be removed without a need to Err bitreich.org 70 i+ * traverse the list. New elements can be added to the list before or Err bitreich.org 70 i+ * after an existing element, at the head of the list, or at the end of Err bitreich.org 70 i+ * the list. A tail queue may be traversed in either direction. Err bitreich.org 70 i+ * Err bitreich.org 70 i+ * An XOR simple queue is used in the same way as a regular simple queue. Err bitreich.org 70 i+ * The difference is that the head structure also includes a "cookie" that Err bitreich.org 70 i+ * is XOR'd with the queue pointer (first, last or next) to generate the Err bitreich.org 70 i+ * real pointer value. Err bitreich.org 70 i+ * Err bitreich.org 70 i+ * For details on the use of these macros, see the queue(3) manual page. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+ Err bitreich.org 70 i+#if defined(QUEUE_MACRO_DEBUG) || (defined(_KERNEL) && defined(DIAGNOSTIC)) Err bitreich.org 70 i+#define _Q_INVALID ((void *)-1) Err bitreich.org 70 i+#define _Q_INVALIDATE(a) (a) = _Q_INVALID Err bitreich.org 70 i+#else Err bitreich.org 70 i+#define _Q_INVALIDATE(a) Err bitreich.org 70 i+#endif Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * Singly-linked List definitions. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define SLIST_HEAD(name, type) \ Err bitreich.org 70 i+struct name { \ Err bitreich.org 70 i+ struct type *slh_first; /* first element */ \ Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SLIST_HEAD_INITIALIZER(head) \ Err bitreich.org 70 i+ { NULL } Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SLIST_ENTRY(type) \ Err bitreich.org 70 i+struct { \ Err bitreich.org 70 i+ struct type *sle_next; /* next element */ \ Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * Singly-linked List access methods. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define SLIST_FIRST(head) ((head)->slh_first) Err bitreich.org 70 i+#define SLIST_END(head) NULL Err bitreich.org 70 i+#define SLIST_EMPTY(head) (SLIST_FIRST(head) == SLIST_END(head)) Err bitreich.org 70 i+#define SLIST_NEXT(elm, field) ((elm)->field.sle_next) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SLIST_FOREACH(var, head, field) \ Err bitreich.org 70 i+ for((var) = SLIST_FIRST(head); \ Err bitreich.org 70 i+ (var) != SLIST_END(head); \ Err bitreich.org 70 i+ (var) = SLIST_NEXT(var, field)) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SLIST_FOREACH_SAFE(var, head, field, tvar) \ Err bitreich.org 70 i+ for ((var) = SLIST_FIRST(head); \ Err bitreich.org 70 i+ (var) && ((tvar) = SLIST_NEXT(var, field), 1); \ Err bitreich.org 70 i+ (var) = (tvar)) Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * Singly-linked List functions. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define SLIST_INIT(head) { \ Err bitreich.org 70 i+ SLIST_FIRST(head) = SLIST_END(head); \ Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SLIST_INSERT_AFTER(slistelm, elm, field) do { \ Err bitreich.org 70 i+ (elm)->field.sle_next = (slistelm)->field.sle_next; \ Err bitreich.org 70 i+ (slistelm)->field.sle_next = (elm); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SLIST_INSERT_HEAD(head, elm, field) do { \ Err bitreich.org 70 i+ (elm)->field.sle_next = (head)->slh_first; \ Err bitreich.org 70 i+ (head)->slh_first = (elm); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SLIST_REMOVE_AFTER(elm, field) do { \ Err bitreich.org 70 i+ (elm)->field.sle_next = (elm)->field.sle_next->field.sle_next; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SLIST_REMOVE_HEAD(head, field) do { \ Err bitreich.org 70 i+ (head)->slh_first = (head)->slh_first->field.sle_next; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SLIST_REMOVE(head, elm, type, field) do { \ Err bitreich.org 70 i+ if ((head)->slh_first == (elm)) { \ Err bitreich.org 70 i+ SLIST_REMOVE_HEAD((head), field); \ Err bitreich.org 70 i+ } else { \ Err bitreich.org 70 i+ struct type *curelm = (head)->slh_first; \ Err bitreich.org 70 i+ \ Err bitreich.org 70 i+ while (curelm->field.sle_next != (elm)) \ Err bitreich.org 70 i+ curelm = curelm->field.sle_next; \ Err bitreich.org 70 i+ curelm->field.sle_next = \ Err bitreich.org 70 i+ curelm->field.sle_next->field.sle_next; \ Err bitreich.org 70 i+ } \ Err bitreich.org 70 i+ _Q_INVALIDATE((elm)->field.sle_next); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * List definitions. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define LIST_HEAD(name, type) \ Err bitreich.org 70 i+struct name { \ Err bitreich.org 70 i+ struct type *lh_first; /* first element */ \ Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+#define LIST_HEAD_INITIALIZER(head) \ Err bitreich.org 70 i+ { NULL } Err bitreich.org 70 i+ Err bitreich.org 70 i+#define LIST_ENTRY(type) \ Err bitreich.org 70 i+struct { \ Err bitreich.org 70 i+ struct type *le_next; /* next element */ \ Err bitreich.org 70 i+ struct type **le_prev; /* address of previous next element */ \ Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * List access methods. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define LIST_FIRST(head) ((head)->lh_first) Err bitreich.org 70 i+#define LIST_END(head) NULL Err bitreich.org 70 i+#define LIST_EMPTY(head) (LIST_FIRST(head) == LIST_END(head)) Err bitreich.org 70 i+#define LIST_NEXT(elm, field) ((elm)->field.le_next) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define LIST_FOREACH(var, head, field) \ Err bitreich.org 70 i+ for((var) = LIST_FIRST(head); \ Err bitreich.org 70 i+ (var)!= LIST_END(head); \ Err bitreich.org 70 i+ (var) = LIST_NEXT(var, field)) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define LIST_FOREACH_SAFE(var, head, field, tvar) \ Err bitreich.org 70 i+ for ((var) = LIST_FIRST(head); \ Err bitreich.org 70 i+ (var) && ((tvar) = LIST_NEXT(var, field), 1); \ Err bitreich.org 70 i+ (var) = (tvar)) Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * List functions. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define LIST_INIT(head) do { \ Err bitreich.org 70 i+ LIST_FIRST(head) = LIST_END(head); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define LIST_INSERT_AFTER(listelm, elm, field) do { \ Err bitreich.org 70 i+ if (((elm)->field.le_next = (listelm)->field.le_next) != NULL) \ Err bitreich.org 70 i+ (listelm)->field.le_next->field.le_prev = \ Err bitreich.org 70 i+ &(elm)->field.le_next; \ Err bitreich.org 70 i+ (listelm)->field.le_next = (elm); \ Err bitreich.org 70 i+ (elm)->field.le_prev = &(listelm)->field.le_next; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define LIST_INSERT_BEFORE(listelm, elm, field) do { \ Err bitreich.org 70 i+ (elm)->field.le_prev = (listelm)->field.le_prev; \ Err bitreich.org 70 i+ (elm)->field.le_next = (listelm); \ Err bitreich.org 70 i+ *(listelm)->field.le_prev = (elm); \ Err bitreich.org 70 i+ (listelm)->field.le_prev = &(elm)->field.le_next; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define LIST_INSERT_HEAD(head, elm, field) do { \ Err bitreich.org 70 i+ if (((elm)->field.le_next = (head)->lh_first) != NULL) \ Err bitreich.org 70 i+ (head)->lh_first->field.le_prev = &(elm)->field.le_next;\ Err bitreich.org 70 i+ (head)->lh_first = (elm); \ Err bitreich.org 70 i+ (elm)->field.le_prev = &(head)->lh_first; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define LIST_REMOVE(elm, field) do { \ Err bitreich.org 70 i+ if ((elm)->field.le_next != NULL) \ Err bitreich.org 70 i+ (elm)->field.le_next->field.le_prev = \ Err bitreich.org 70 i+ (elm)->field.le_prev; \ Err bitreich.org 70 i+ *(elm)->field.le_prev = (elm)->field.le_next; \ Err bitreich.org 70 i+ _Q_INVALIDATE((elm)->field.le_prev); \ Err bitreich.org 70 i+ _Q_INVALIDATE((elm)->field.le_next); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define LIST_REPLACE(elm, elm2, field) do { \ Err bitreich.org 70 i+ if (((elm2)->field.le_next = (elm)->field.le_next) != NULL) \ Err bitreich.org 70 i+ (elm2)->field.le_next->field.le_prev = \ Err bitreich.org 70 i+ &(elm2)->field.le_next; \ Err bitreich.org 70 i+ (elm2)->field.le_prev = (elm)->field.le_prev; \ Err bitreich.org 70 i+ *(elm2)->field.le_prev = (elm2); \ Err bitreich.org 70 i+ _Q_INVALIDATE((elm)->field.le_prev); \ Err bitreich.org 70 i+ _Q_INVALIDATE((elm)->field.le_next); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * Simple queue definitions. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define SIMPLEQ_HEAD(name, type) \ Err bitreich.org 70 i+struct name { \ Err bitreich.org 70 i+ struct type *sqh_first; /* first element */ \ Err bitreich.org 70 i+ struct type **sqh_last; /* addr of last next element */ \ Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SIMPLEQ_HEAD_INITIALIZER(head) \ Err bitreich.org 70 i+ { NULL, &(head).sqh_first } Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SIMPLEQ_ENTRY(type) \ Err bitreich.org 70 i+struct { \ Err bitreich.org 70 i+ struct type *sqe_next; /* next element */ \ Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * Simple queue access methods. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define SIMPLEQ_FIRST(head) ((head)->sqh_first) Err bitreich.org 70 i+#define SIMPLEQ_END(head) NULL Err bitreich.org 70 i+#define SIMPLEQ_EMPTY(head) (SIMPLEQ_FIRST(head) == SIMPLEQ_END(head)) Err bitreich.org 70 i+#define SIMPLEQ_NEXT(elm, field) ((elm)->field.sqe_next) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SIMPLEQ_FOREACH(var, head, field) \ Err bitreich.org 70 i+ for((var) = SIMPLEQ_FIRST(head); \ Err bitreich.org 70 i+ (var) != SIMPLEQ_END(head); \ Err bitreich.org 70 i+ (var) = SIMPLEQ_NEXT(var, field)) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SIMPLEQ_FOREACH_SAFE(var, head, field, tvar) \ Err bitreich.org 70 i+ for ((var) = SIMPLEQ_FIRST(head); \ Err bitreich.org 70 i+ (var) && ((tvar) = SIMPLEQ_NEXT(var, field), 1); \ Err bitreich.org 70 i+ (var) = (tvar)) Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * Simple queue functions. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define SIMPLEQ_INIT(head) do { \ Err bitreich.org 70 i+ (head)->sqh_first = NULL; \ Err bitreich.org 70 i+ (head)->sqh_last = &(head)->sqh_first; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SIMPLEQ_INSERT_HEAD(head, elm, field) do { \ Err bitreich.org 70 i+ if (((elm)->field.sqe_next = (head)->sqh_first) == NULL) \ Err bitreich.org 70 i+ (head)->sqh_last = &(elm)->field.sqe_next; \ Err bitreich.org 70 i+ (head)->sqh_first = (elm); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SIMPLEQ_INSERT_TAIL(head, elm, field) do { \ Err bitreich.org 70 i+ (elm)->field.sqe_next = NULL; \ Err bitreich.org 70 i+ *(head)->sqh_last = (elm); \ Err bitreich.org 70 i+ (head)->sqh_last = &(elm)->field.sqe_next; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SIMPLEQ_INSERT_AFTER(head, listelm, elm, field) do { \ Err bitreich.org 70 i+ if (((elm)->field.sqe_next = (listelm)->field.sqe_next) == NULL)\ Err bitreich.org 70 i+ (head)->sqh_last = &(elm)->field.sqe_next; \ Err bitreich.org 70 i+ (listelm)->field.sqe_next = (elm); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SIMPLEQ_REMOVE_HEAD(head, field) do { \ Err bitreich.org 70 i+ if (((head)->sqh_first = (head)->sqh_first->field.sqe_next) == NULL) \ Err bitreich.org 70 i+ (head)->sqh_last = &(head)->sqh_first; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SIMPLEQ_REMOVE_AFTER(head, elm, field) do { \ Err bitreich.org 70 i+ if (((elm)->field.sqe_next = (elm)->field.sqe_next->field.sqe_next) \ Err bitreich.org 70 i+ == NULL) \ Err bitreich.org 70 i+ (head)->sqh_last = &(elm)->field.sqe_next; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define SIMPLEQ_CONCAT(head1, head2) do { \ Err bitreich.org 70 i+ if (!SIMPLEQ_EMPTY((head2))) { \ Err bitreich.org 70 i+ *(head1)->sqh_last = (head2)->sqh_first; \ Err bitreich.org 70 i+ (head1)->sqh_last = (head2)->sqh_last; \ Err bitreich.org 70 i+ SIMPLEQ_INIT((head2)); \ Err bitreich.org 70 i+ } \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * XOR Simple queue definitions. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define XSIMPLEQ_HEAD(name, type) \ Err bitreich.org 70 i+struct name { \ Err bitreich.org 70 i+ struct type *sqx_first; /* first element */ \ Err bitreich.org 70 i+ struct type **sqx_last; /* addr of last next element */ \ Err bitreich.org 70 i+ unsigned long sqx_cookie; \ Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+#define XSIMPLEQ_ENTRY(type) \ Err bitreich.org 70 i+struct { \ Err bitreich.org 70 i+ struct type *sqx_next; /* next element */ \ Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * XOR Simple queue access methods. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define XSIMPLEQ_XOR(head, ptr) ((__typeof(ptr))((head)->sqx_cookie ^ \ Err bitreich.org 70 i+ (unsigned long)(ptr))) Err bitreich.org 70 i+#define XSIMPLEQ_FIRST(head) XSIMPLEQ_XOR(head, ((head)->sqx_first)) Err bitreich.org 70 i+#define XSIMPLEQ_END(head) NULL Err bitreich.org 70 i+#define XSIMPLEQ_EMPTY(head) (XSIMPLEQ_FIRST(head) == XSIMPLEQ_END(head)) Err bitreich.org 70 i+#define XSIMPLEQ_NEXT(head, elm, field) XSIMPLEQ_XOR(head, ((elm)->field.sqx_next)) Err bitreich.org 70 i+ Err bitreich.org 70 i+ Err bitreich.org 70 i+#define XSIMPLEQ_FOREACH(var, head, field) \ Err bitreich.org 70 i+ for ((var) = XSIMPLEQ_FIRST(head); \ Err bitreich.org 70 i+ (var) != XSIMPLEQ_END(head); \ Err bitreich.org 70 i+ (var) = XSIMPLEQ_NEXT(head, var, field)) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define XSIMPLEQ_FOREACH_SAFE(var, head, field, tvar) \ Err bitreich.org 70 i+ for ((var) = XSIMPLEQ_FIRST(head); \ Err bitreich.org 70 i+ (var) && ((tvar) = XSIMPLEQ_NEXT(head, var, field), 1); \ Err bitreich.org 70 i+ (var) = (tvar)) Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * XOR Simple queue functions. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define XSIMPLEQ_INIT(head) do { \ Err bitreich.org 70 i+ arc4random_buf(&(head)->sqx_cookie, sizeof((head)->sqx_cookie)); \ Err bitreich.org 70 i+ (head)->sqx_first = XSIMPLEQ_XOR(head, NULL); \ Err bitreich.org 70 i+ (head)->sqx_last = XSIMPLEQ_XOR(head, &(head)->sqx_first); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define XSIMPLEQ_INSERT_HEAD(head, elm, field) do { \ Err bitreich.org 70 i+ if (((elm)->field.sqx_next = (head)->sqx_first) == \ Err bitreich.org 70 i+ XSIMPLEQ_XOR(head, NULL)) \ Err bitreich.org 70 i+ (head)->sqx_last = XSIMPLEQ_XOR(head, &(elm)->field.sqx_next); \ Err bitreich.org 70 i+ (head)->sqx_first = XSIMPLEQ_XOR(head, (elm)); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define XSIMPLEQ_INSERT_TAIL(head, elm, field) do { \ Err bitreich.org 70 i+ (elm)->field.sqx_next = XSIMPLEQ_XOR(head, NULL); \ Err bitreich.org 70 i+ *(XSIMPLEQ_XOR(head, (head)->sqx_last)) = XSIMPLEQ_XOR(head, (elm)); \ Err bitreich.org 70 i+ (head)->sqx_last = XSIMPLEQ_XOR(head, &(elm)->field.sqx_next); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define XSIMPLEQ_INSERT_AFTER(head, listelm, elm, field) do { \ Err bitreich.org 70 i+ if (((elm)->field.sqx_next = (listelm)->field.sqx_next) == \ Err bitreich.org 70 i+ XSIMPLEQ_XOR(head, NULL)) \ Err bitreich.org 70 i+ (head)->sqx_last = XSIMPLEQ_XOR(head, &(elm)->field.sqx_next); \ Err bitreich.org 70 i+ (listelm)->field.sqx_next = XSIMPLEQ_XOR(head, (elm)); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define XSIMPLEQ_REMOVE_HEAD(head, field) do { \ Err bitreich.org 70 i+ if (((head)->sqx_first = XSIMPLEQ_XOR(head, \ Err bitreich.org 70 i+ (head)->sqx_first)->field.sqx_next) == XSIMPLEQ_XOR(head, NULL)) \ Err bitreich.org 70 i+ (head)->sqx_last = XSIMPLEQ_XOR(head, &(head)->sqx_first); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define XSIMPLEQ_REMOVE_AFTER(head, elm, field) do { \ Err bitreich.org 70 i+ if (((elm)->field.sqx_next = XSIMPLEQ_XOR(head, \ Err bitreich.org 70 i+ (elm)->field.sqx_next)->field.sqx_next) \ Err bitreich.org 70 i+ == XSIMPLEQ_XOR(head, NULL)) \ Err bitreich.org 70 i+ (head)->sqx_last = \ Err bitreich.org 70 i+ XSIMPLEQ_XOR(head, &(elm)->field.sqx_next); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * Tail queue definitions. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define TAILQ_HEAD(name, type) \ Err bitreich.org 70 i+struct name { \ Err bitreich.org 70 i+ struct type *tqh_first; /* first element */ \ Err bitreich.org 70 i+ struct type **tqh_last; /* addr of last next element */ \ Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_HEAD_INITIALIZER(head) \ Err bitreich.org 70 i+ { NULL, &(head).tqh_first } Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_ENTRY(type) \ Err bitreich.org 70 i+struct { \ Err bitreich.org 70 i+ struct type *tqe_next; /* next element */ \ Err bitreich.org 70 i+ struct type **tqe_prev; /* address of previous next element */ \ Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * Tail queue access methods. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define TAILQ_FIRST(head) ((head)->tqh_first) Err bitreich.org 70 i+#define TAILQ_END(head) NULL Err bitreich.org 70 i+#define TAILQ_NEXT(elm, field) ((elm)->field.tqe_next) Err bitreich.org 70 i+#define TAILQ_LAST(head, headname) \ Err bitreich.org 70 i+ (*(((struct headname *)((head)->tqh_last))->tqh_last)) Err bitreich.org 70 i+/* XXX */ Err bitreich.org 70 i+#define TAILQ_PREV(elm, headname, field) \ Err bitreich.org 70 i+ (*(((struct headname *)((elm)->field.tqe_prev))->tqh_last)) Err bitreich.org 70 i+#define TAILQ_EMPTY(head) \ Err bitreich.org 70 i+ (TAILQ_FIRST(head) == TAILQ_END(head)) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_FOREACH(var, head, field) \ Err bitreich.org 70 i+ for((var) = TAILQ_FIRST(head); \ Err bitreich.org 70 i+ (var) != TAILQ_END(head); \ Err bitreich.org 70 i+ (var) = TAILQ_NEXT(var, field)) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_FOREACH_SAFE(var, head, field, tvar) \ Err bitreich.org 70 i+ for ((var) = TAILQ_FIRST(head); \ Err bitreich.org 70 i+ (var) != TAILQ_END(head) && \ Err bitreich.org 70 i+ ((tvar) = TAILQ_NEXT(var, field), 1); \ Err bitreich.org 70 i+ (var) = (tvar)) Err bitreich.org 70 i+ Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_FOREACH_REVERSE(var, head, headname, field) \ Err bitreich.org 70 i+ for((var) = TAILQ_LAST(head, headname); \ Err bitreich.org 70 i+ (var) != TAILQ_END(head); \ Err bitreich.org 70 i+ (var) = TAILQ_PREV(var, headname, field)) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_FOREACH_REVERSE_SAFE(var, head, headname, field, tvar) \ Err bitreich.org 70 i+ for ((var) = TAILQ_LAST(head, headname); \ Err bitreich.org 70 i+ (var) != TAILQ_END(head) && \ Err bitreich.org 70 i+ ((tvar) = TAILQ_PREV(var, headname, field), 1); \ Err bitreich.org 70 i+ (var) = (tvar)) Err bitreich.org 70 i+ Err bitreich.org 70 i+/* Err bitreich.org 70 i+ * Tail queue functions. Err bitreich.org 70 i+ */ Err bitreich.org 70 i+#define TAILQ_INIT(head) do { \ Err bitreich.org 70 i+ (head)->tqh_first = NULL; \ Err bitreich.org 70 i+ (head)->tqh_last = &(head)->tqh_first; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_INSERT_HEAD(head, elm, field) do { \ Err bitreich.org 70 i+ if (((elm)->field.tqe_next = (head)->tqh_first) != NULL) \ Err bitreich.org 70 i+ (head)->tqh_first->field.tqe_prev = \ Err bitreich.org 70 i+ &(elm)->field.tqe_next; \ Err bitreich.org 70 i+ else \ Err bitreich.org 70 i+ (head)->tqh_last = &(elm)->field.tqe_next; \ Err bitreich.org 70 i+ (head)->tqh_first = (elm); \ Err bitreich.org 70 i+ (elm)->field.tqe_prev = &(head)->tqh_first; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_INSERT_TAIL(head, elm, field) do { \ Err bitreich.org 70 i+ (elm)->field.tqe_next = NULL; \ Err bitreich.org 70 i+ (elm)->field.tqe_prev = (head)->tqh_last; \ Err bitreich.org 70 i+ *(head)->tqh_last = (elm); \ Err bitreich.org 70 i+ (head)->tqh_last = &(elm)->field.tqe_next; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_INSERT_AFTER(head, listelm, elm, field) do { \ Err bitreich.org 70 i+ if (((elm)->field.tqe_next = (listelm)->field.tqe_next) != NULL)\ Err bitreich.org 70 i+ (elm)->field.tqe_next->field.tqe_prev = \ Err bitreich.org 70 i+ &(elm)->field.tqe_next; \ Err bitreich.org 70 i+ else \ Err bitreich.org 70 i+ (head)->tqh_last = &(elm)->field.tqe_next; \ Err bitreich.org 70 i+ (listelm)->field.tqe_next = (elm); \ Err bitreich.org 70 i+ (elm)->field.tqe_prev = &(listelm)->field.tqe_next; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_INSERT_BEFORE(listelm, elm, field) do { \ Err bitreich.org 70 i+ (elm)->field.tqe_prev = (listelm)->field.tqe_prev; \ Err bitreich.org 70 i+ (elm)->field.tqe_next = (listelm); \ Err bitreich.org 70 i+ *(listelm)->field.tqe_prev = (elm); \ Err bitreich.org 70 i+ (listelm)->field.tqe_prev = &(elm)->field.tqe_next; \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_REMOVE(head, elm, field) do { \ Err bitreich.org 70 i+ if (((elm)->field.tqe_next) != NULL) \ Err bitreich.org 70 i+ (elm)->field.tqe_next->field.tqe_prev = \ Err bitreich.org 70 i+ (elm)->field.tqe_prev; \ Err bitreich.org 70 i+ else \ Err bitreich.org 70 i+ (head)->tqh_last = (elm)->field.tqe_prev; \ Err bitreich.org 70 i+ *(elm)->field.tqe_prev = (elm)->field.tqe_next; \ Err bitreich.org 70 i+ _Q_INVALIDATE((elm)->field.tqe_prev); \ Err bitreich.org 70 i+ _Q_INVALIDATE((elm)->field.tqe_next); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_REPLACE(head, elm, elm2, field) do { \ Err bitreich.org 70 i+ if (((elm2)->field.tqe_next = (elm)->field.tqe_next) != NULL) \ Err bitreich.org 70 i+ (elm2)->field.tqe_next->field.tqe_prev = \ Err bitreich.org 70 i+ &(elm2)->field.tqe_next; \ Err bitreich.org 70 i+ else \ Err bitreich.org 70 i+ (head)->tqh_last = &(elm2)->field.tqe_next; \ Err bitreich.org 70 i+ (elm2)->field.tqe_prev = (elm)->field.tqe_prev; \ Err bitreich.org 70 i+ *(elm2)->field.tqe_prev = (elm2); \ Err bitreich.org 70 i+ _Q_INVALIDATE((elm)->field.tqe_prev); \ Err bitreich.org 70 i+ _Q_INVALIDATE((elm)->field.tqe_next); \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#define TAILQ_CONCAT(head1, head2, field) do { \ Err bitreich.org 70 i+ if (!TAILQ_EMPTY(head2)) { \ Err bitreich.org 70 i+ *(head1)->tqh_last = (head2)->tqh_first; \ Err bitreich.org 70 i+ (head2)->tqh_first->field.tqe_prev = (head1)->tqh_last; \ Err bitreich.org 70 i+ (head1)->tqh_last = (head2)->tqh_last; \ Err bitreich.org 70 i+ TAILQ_INIT((head2)); \ Err bitreich.org 70 i+ } \ Err bitreich.org 70 i+} while (0) Err bitreich.org 70 i+ Err bitreich.org 70 i+#endif /* !_SYS_QUEUE_H_ */ Err bitreich.org 70 1diff --git a/snap.c b/snap.c /scm/dedup/file/snap.c.gph bitreich.org 70 i@@ -0,0 +1,249 @@ Err bitreich.org 70 i+/* Snapshot archive implementation */ Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+ Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+#include Err bitreich.org 70 i+ Err bitreich.org 70 i+#include "config.h" Err bitreich.org 70 i+#include "queue.h" Err bitreich.org 70 i+#include "snap.h" Err bitreich.org 70 i+ Err bitreich.org 70 i+extern int pack(unsigned char *dst, char *fmt, ...); Err bitreich.org 70 i+extern int unpack(unsigned char *src, char *fmt, ...); Err bitreich.org 70 i+ Err bitreich.org 70 i+struct mdnode { Err bitreich.org 70 i+ unsigned char md[MDSIZE]; Err bitreich.org 70 i+ SLIST_ENTRY(mdnode) e; Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+struct sctx { Err bitreich.org 70 i+ SLIST_HEAD(mdhead, mdnode) mdhead; Err bitreich.org 70 i+ struct mdnode *mdnext; Err bitreich.org 70 i+ int fd; Err bitreich.org 70 i+ int rdonly; Err bitreich.org 70 i+}; Err bitreich.org 70 i+ Err bitreich.org 70 i+static ssize_t Err bitreich.org 70 i+xread(int fd, void *buf, size_t nbytes) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ uint8_t *bp = buf; Err bitreich.org 70 i+ ssize_t total = 0; Err bitreich.org 70 i+ Err bitreich.org 70 i+ while (nbytes > 0) { Err bitreich.org 70 i+ ssize_t n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ n = read(fd, &bp[total], nbytes); Err bitreich.org 70 i+ if (n < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ else if (n == 0) Err bitreich.org 70 i+ return total; Err bitreich.org 70 i+ total += n; Err bitreich.org 70 i+ nbytes -= n; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return total; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static ssize_t Err bitreich.org 70 i+xwrite(int fd, void *buf, size_t nbytes) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ uint8_t *bp = buf; Err bitreich.org 70 i+ ssize_t total = 0; Err bitreich.org 70 i+ Err bitreich.org 70 i+ while (nbytes > 0) { Err bitreich.org 70 i+ ssize_t n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ n = write(fd, &bp[total], nbytes); Err bitreich.org 70 i+ if (n < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ else if (n == 0) Err bitreich.org 70 i+ return total; Err bitreich.org 70 i+ total += n; Err bitreich.org 70 i+ nbytes -= n; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return total; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+loadmd(struct sctx *sctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct mdnode *mdnode; Err bitreich.org 70 i+ Err bitreich.org 70 i+ mdnode = calloc(1, sizeof(*mdnode)); Err bitreich.org 70 i+ if (mdnode == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ if (xread(sctx->fd, mdnode->md, MDSIZE) != MDSIZE) { Err bitreich.org 70 i+ free(mdnode); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ SLIST_INSERT_HEAD(&sctx->mdhead, mdnode, e); Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+static int Err bitreich.org 70 i+initmdhead(struct sctx *sctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct stat st; Err bitreich.org 70 i+ uint64_t i, n; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (fstat(sctx->fd, &st) < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ n = st.st_size / MDSIZE; Err bitreich.org 70 i+ for (i = 0; i < n; i++) { Err bitreich.org 70 i+ if (loadmd(sctx) == 0) Err bitreich.org 70 i+ continue; Err bitreich.org 70 i+ Err bitreich.org 70 i+ /* Cleanup */ Err bitreich.org 70 i+ while (!SLIST_EMPTY(&sctx->mdhead)) { Err bitreich.org 70 i+ struct mdnode *mdnode; Err bitreich.org 70 i+ Err bitreich.org 70 i+ mdnode = SLIST_FIRST(&sctx->mdhead); Err bitreich.org 70 i+ SLIST_REMOVE(&sctx->mdhead, mdnode, mdnode, e); Err bitreich.org 70 i+ free(mdnode); Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+screat(char *path, int mode, struct sctx **sctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ int fd; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (path == NULL || sctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ fd = open(path, O_RDWR | O_CREAT | O_EXCL, mode); Err bitreich.org 70 i+ if (fd < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ *sctx = calloc(1, sizeof(**sctx)); Err bitreich.org 70 i+ if (*sctx == NULL) { Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ SLIST_INIT(&(*sctx)->mdhead); Err bitreich.org 70 i+ (*sctx)->mdnext = NULL; Err bitreich.org 70 i+ (*sctx)->fd = fd; Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+sopen(char *path, int flags, int mode, struct sctx **sctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ int fd; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (path == NULL || sctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ fd = open(path, flags, mode); Err bitreich.org 70 i+ if (fd < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ *sctx = calloc(1, sizeof(*sctx)); Err bitreich.org 70 i+ if (*sctx == NULL) { Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ SLIST_INIT(&(*sctx)->mdhead); Err bitreich.org 70 i+ (*sctx)->mdnext = NULL; Err bitreich.org 70 i+ (*sctx)->fd = fd; Err bitreich.org 70 i+ (*sctx)->rdonly = flags == O_RDONLY; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (initmdhead(*sctx) < 0) { Err bitreich.org 70 i+ free(*sctx); Err bitreich.org 70 i+ close(fd); Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+sget(struct sctx *sctx, unsigned char *md) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct mdnode *mdnode; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (sctx == NULL || md == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ mdnode = sctx->mdnext; Err bitreich.org 70 i+ if (mdnode == NULL) Err bitreich.org 70 i+ mdnode = SLIST_FIRST(&sctx->mdhead); Err bitreich.org 70 i+ else Err bitreich.org 70 i+ mdnode = SLIST_NEXT(mdnode, e); Err bitreich.org 70 i+ sctx->mdnext = mdnode; Err bitreich.org 70 i+ if (mdnode != NULL) { Err bitreich.org 70 i+ memcpy(md, mdnode->md, MDSIZE); Err bitreich.org 70 i+ return MDSIZE; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+sput(struct sctx *sctx, unsigned char *md) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct mdnode *mdnode; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (sctx == NULL || md == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ mdnode = calloc(1, sizeof(*mdnode)); Err bitreich.org 70 i+ if (mdnode == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ memcpy(mdnode->md, md, MDSIZE); Err bitreich.org 70 i+ SLIST_INSERT_HEAD(&sctx->mdhead, mdnode, e); Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+ssync(struct sctx *sctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ struct mdnode *mdnode; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (sctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (sctx->rdonly) Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (lseek(sctx->fd, 0, SEEK_SET) < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ SLIST_FOREACH(mdnode, &sctx->mdhead, e) { Err bitreich.org 70 i+ if (xwrite(sctx->fd, mdnode->md, MDSIZE) != MDSIZE) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ } Err bitreich.org 70 i+ fsync(sctx->fd); Err bitreich.org 70 i+ return 0; Err bitreich.org 70 i+} Err bitreich.org 70 i+ Err bitreich.org 70 i+int Err bitreich.org 70 i+sclose(struct sctx *sctx) Err bitreich.org 70 i+{ Err bitreich.org 70 i+ int r; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (sctx == NULL) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ if (ssync(sctx) < 0) Err bitreich.org 70 i+ return -1; Err bitreich.org 70 i+ Err bitreich.org 70 i+ /* Cleanup */ Err bitreich.org 70 i+ while (!SLIST_EMPTY(&sctx->mdhead)) { Err bitreich.org 70 i+ struct mdnode *mdnode; Err bitreich.org 70 i+ Err bitreich.org 70 i+ mdnode = SLIST_FIRST(&sctx->mdhead); Err bitreich.org 70 i+ SLIST_REMOVE(&sctx->mdhead, mdnode, mdnode, e); Err bitreich.org 70 i+ free(mdnode); Err bitreich.org 70 i+ } Err bitreich.org 70 i+ Err bitreich.org 70 i+ r = close(sctx->fd); Err bitreich.org 70 i+ free(sctx); Err bitreich.org 70 i+ return r; Err bitreich.org 70 i+} Err bitreich.org 70 1diff --git a/snap.h b/snap.h /scm/dedup/file/snap.h.gph bitreich.org 70 i@@ -0,0 +1,8 @@ Err bitreich.org 70 i+struct sctx; Err bitreich.org 70 i+ Err bitreich.org 70 i+extern int screat(char *path, int mode, struct sctx **sctx); Err bitreich.org 70 i+extern int sopen(char *path, int flags, int mode, struct sctx **sctx); Err bitreich.org 70 i+extern int sget(struct sctx *sctx, unsigned char *md); Err bitreich.org 70 i+extern int sput(struct sctx *sctx, unsigned char *md); Err bitreich.org 70 i+extern int ssync(struct sctx *sctx); Err bitreich.org 70 i+extern int sclose(struct sctx *sctx); Err bitreich.org 70 1diff --git a/types.c b/types.c /scm/dedup/file/types.c.gph bitreich.org 70 i@@ -1,192 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-read_snap_hdr(int fd, struct snap_hdr *hdr) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t buf[SNAP_HDR_SIZE]; Err bitreich.org 70 i- int n; Err bitreich.org 70 i- Err bitreich.org 70 i- if (xread(fd, buf, sizeof(buf)) == 0) Err bitreich.org 70 i- errx(1, "%s: unexpected EOF", __func__); Err bitreich.org 70 i- Err bitreich.org 70 i- n = unpack(buf, "qqq", Err bitreich.org 70 i- &hdr->flags, Err bitreich.org 70 i- &hdr->size, Err bitreich.org 70 i- &hdr->nr_snaps); Err bitreich.org 70 i- Err bitreich.org 70 i- n += unpack(&buf[n], "qqqqqq", Err bitreich.org 70 i- &hdr->st.orig_size, Err bitreich.org 70 i- &hdr->st.compr_size, Err bitreich.org 70 i- &hdr->st.dedup_size, Err bitreich.org 70 i- &hdr->st.min_blk_size, Err bitreich.org 70 i- &hdr->st.max_blk_size, Err bitreich.org 70 i- &hdr->st.nr_blks); Err bitreich.org 70 i- Err bitreich.org 70 i- n += unpack(&buf[n], "qqqq", Err bitreich.org 70 i- &hdr->st.reserved[0], Err bitreich.org 70 i- &hdr->st.reserved[1], Err bitreich.org 70 i- &hdr->st.reserved[2], Err bitreich.org 70 i- &hdr->st.reserved[3]); Err bitreich.org 70 i- Err bitreich.org 70 i- assert(n == SNAP_HDR_SIZE); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-write_snap_hdr(int fd, struct snap_hdr *hdr) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t buf[SNAP_HDR_SIZE]; Err bitreich.org 70 i- int n; Err bitreich.org 70 i- Err bitreich.org 70 i- n = pack(buf, "qqq", Err bitreich.org 70 i- hdr->flags, Err bitreich.org 70 i- hdr->size, Err bitreich.org 70 i- hdr->nr_snaps); Err bitreich.org 70 i- Err bitreich.org 70 i- n += pack(&buf[n], "qqqqqq", Err bitreich.org 70 i- hdr->st.orig_size, Err bitreich.org 70 i- hdr->st.compr_size, Err bitreich.org 70 i- hdr->st.dedup_size, Err bitreich.org 70 i- hdr->st.min_blk_size, Err bitreich.org 70 i- hdr->st.max_blk_size, Err bitreich.org 70 i- hdr->st.nr_blks); Err bitreich.org 70 i- Err bitreich.org 70 i- n += pack(&buf[n], "qqqq", Err bitreich.org 70 i- hdr->st.reserved[0], Err bitreich.org 70 i- hdr->st.reserved[1], Err bitreich.org 70 i- hdr->st.reserved[2], Err bitreich.org 70 i- hdr->st.reserved[3]); Err bitreich.org 70 i- Err bitreich.org 70 i- assert(n == SNAP_HDR_SIZE); Err bitreich.org 70 i- xwrite(fd, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-read_blk_hdr(int fd, struct blk_hdr *hdr) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t buf[BLK_HDR_SIZE]; Err bitreich.org 70 i- int n; Err bitreich.org 70 i- Err bitreich.org 70 i- if (xread(fd, buf, sizeof(buf)) == 0) Err bitreich.org 70 i- errx(1, "%s: unexpected EOF", __func__); Err bitreich.org 70 i- Err bitreich.org 70 i- n = unpack(buf, "qq", Err bitreich.org 70 i- &hdr->flags, Err bitreich.org 70 i- &hdr->size); Err bitreich.org 70 i- Err bitreich.org 70 i- assert(n == BLK_HDR_SIZE); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-write_blk_hdr(int fd, struct blk_hdr *hdr) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t buf[BLK_HDR_SIZE]; Err bitreich.org 70 i- int n; Err bitreich.org 70 i- Err bitreich.org 70 i- n = pack(buf, "qq", Err bitreich.org 70 i- hdr->flags, Err bitreich.org 70 i- hdr->size); Err bitreich.org 70 i- Err bitreich.org 70 i- assert(n == BLK_HDR_SIZE); Err bitreich.org 70 i- xwrite(fd, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-read_blk_desc(int fd, struct blk_desc *desc) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t buf[BLK_DESC_SIZE]; Err bitreich.org 70 i- char fmt[BUFSIZ]; Err bitreich.org 70 i- int n; Err bitreich.org 70 i- Err bitreich.org 70 i- if (xread(fd, buf, sizeof(buf)) == 0) Err bitreich.org 70 i- errx(1, "%s: unexpected EOF", __func__); Err bitreich.org 70 i- Err bitreich.org 70 i- snprintf(fmt, sizeof(fmt), "'%dqq", MD_SIZE); Err bitreich.org 70 i- n = unpack(buf, fmt, Err bitreich.org 70 i- desc->md, Err bitreich.org 70 i- &desc->offset, Err bitreich.org 70 i- &desc->size); Err bitreich.org 70 i- Err bitreich.org 70 i- assert(n == BLK_DESC_SIZE); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-write_blk_desc(int fd, struct blk_desc *desc) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t buf[BLK_DESC_SIZE]; Err bitreich.org 70 i- char fmt[BUFSIZ]; Err bitreich.org 70 i- int n; Err bitreich.org 70 i- Err bitreich.org 70 i- snprintf(fmt, sizeof(fmt), "'%dqq", MD_SIZE); Err bitreich.org 70 i- n = pack(buf, fmt, Err bitreich.org 70 i- desc->md, Err bitreich.org 70 i- desc->offset, Err bitreich.org 70 i- desc->size); Err bitreich.org 70 i- Err bitreich.org 70 i- assert(n == BLK_DESC_SIZE); Err bitreich.org 70 i- xwrite(fd, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-read_snap(int fd, struct snap *snap) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t buf[SNAPSHOT_SIZE]; Err bitreich.org 70 i- char fmt[BUFSIZ]; Err bitreich.org 70 i- int n; Err bitreich.org 70 i- Err bitreich.org 70 i- if (xread(fd, buf, sizeof(buf)) == 0) Err bitreich.org 70 i- errx(1, "%s: unexpected EOF", __func__); Err bitreich.org 70 i- Err bitreich.org 70 i- snprintf(fmt, sizeof(fmt), "q'%d'%dq", MSG_SIZE, MD_SIZE); Err bitreich.org 70 i- n = unpack(buf, fmt, Err bitreich.org 70 i- &snap->size, Err bitreich.org 70 i- snap->msg, Err bitreich.org 70 i- snap->md, Err bitreich.org 70 i- &snap->nr_blk_descs); Err bitreich.org 70 i- Err bitreich.org 70 i- assert(n == SNAPSHOT_SIZE); Err bitreich.org 70 i-}; Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-read_snap_descs(int fd, struct snap *snap) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint64_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- for (i = 0; i < snap->nr_blk_descs; i++) Err bitreich.org 70 i- read_blk_desc(fd, &snap->blk_desc[i]); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-write_snap(int fd, struct snap *snap) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t buf[SNAPSHOT_SIZE]; Err bitreich.org 70 i- char fmt[BUFSIZ]; Err bitreich.org 70 i- int n; Err bitreich.org 70 i- Err bitreich.org 70 i- snprintf(fmt, sizeof(fmt), "q'%d'%dq", MSG_SIZE, MD_SIZE); Err bitreich.org 70 i- n = pack(buf, fmt, Err bitreich.org 70 i- snap->size, Err bitreich.org 70 i- snap->msg, Err bitreich.org 70 i- snap->md, Err bitreich.org 70 i- snap->nr_blk_descs); Err bitreich.org 70 i- Err bitreich.org 70 i- assert(n == SNAPSHOT_SIZE); Err bitreich.org 70 i- xwrite(fd, buf, n); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-write_snap_blk_descs(int fd, struct snap *snap) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint64_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- for (i = 0; i < snap->nr_blk_descs; i++) Err bitreich.org 70 i- write_blk_desc(fd, &snap->blk_desc[i]); Err bitreich.org 70 i-} Err bitreich.org 70 1diff --git a/utils.c b/utils.c /scm/dedup/file/utils.c.gph bitreich.org 70 i@@ -1,288 +0,0 @@ Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i-#include Err bitreich.org 70 i- Err bitreich.org 70 i-#include "blake2.h" Err bitreich.org 70 i-#include "dedup.h" Err bitreich.org 70 i- Err bitreich.org 70 i-static void Err bitreich.org 70 i-match_ver(uint64_t v) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t maj, min; Err bitreich.org 70 i- Err bitreich.org 70 i- min = v & VER_MIN_MASK; Err bitreich.org 70 i- maj = (v >> VER_MAJ_SHIFT) & VER_MAJ_MASK; Err bitreich.org 70 i- if (maj == VER_MAJ && min == VER_MIN) Err bitreich.org 70 i- return; Err bitreich.org 70 i- errx(1, "format version mismatch: expected %u.%u but got %u.%u", Err bitreich.org 70 i- VER_MAJ, VER_MIN, maj, min); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-str2bin(char *s, uint8_t *d) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t i, size = strlen(s) / 2; Err bitreich.org 70 i- Err bitreich.org 70 i- for (i = 0; i < size; i++, s += 2) Err bitreich.org 70 i- sscanf(s, "%2hhx", &d[i]); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-off_t Err bitreich.org 70 i-xlseek(int fd, off_t offset, int whence) Err bitreich.org 70 i-{ Err bitreich.org 70 i- off_t ret; Err bitreich.org 70 i- Err bitreich.org 70 i- ret = lseek(fd, offset, whence); Err bitreich.org 70 i- if (ret < 0) Err bitreich.org 70 i- err(1, "lseek"); Err bitreich.org 70 i- return ret; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-ssize_t Err bitreich.org 70 i-xread(int fd, void *buf, size_t nbytes) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint8_t *bp = buf; Err bitreich.org 70 i- ssize_t total = 0; Err bitreich.org 70 i- Err bitreich.org 70 i- while (nbytes > 0) { Err bitreich.org 70 i- ssize_t n; Err bitreich.org 70 i- Err bitreich.org 70 i- n = read(fd, &bp[total], nbytes); Err bitreich.org 70 i- if (n < 0) Err bitreich.org 70 i- err(1, "read"); Err bitreich.org 70 i- else if (n == 0) Err bitreich.org 70 i- return total; Err bitreich.org 70 i- total += n; Err bitreich.org 70 i- nbytes -= n; Err bitreich.org 70 i- } Err bitreich.org 70 i- return total; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-ssize_t Err bitreich.org 70 i-xwrite(int fd, const void *buf, size_t nbytes) Err bitreich.org 70 i-{ Err bitreich.org 70 i- const uint8_t *bp = buf; Err bitreich.org 70 i- ssize_t total = 0; Err bitreich.org 70 i- Err bitreich.org 70 i- while (nbytes > 0) { Err bitreich.org 70 i- ssize_t n; Err bitreich.org 70 i- Err bitreich.org 70 i- n = write(fd, &bp[total], nbytes); Err bitreich.org 70 i- if (n < 0) Err bitreich.org 70 i- err(1, "write"); Err bitreich.org 70 i- else if (n == 0) Err bitreich.org 70 i- return total; Err bitreich.org 70 i- total += n; Err bitreich.org 70 i- nbytes -= n; Err bitreich.org 70 i- } Err bitreich.org 70 i- return total; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-init_blk_hdr(struct blk_hdr *hdr, int compr_algo, int hash_algo) Err bitreich.org 70 i-{ Err bitreich.org 70 i- hdr->flags = (VER_MAJ << VER_MAJ_SHIFT) | VER_MIN; Err bitreich.org 70 i- hdr->flags |= compr_algo << COMPR_ALGO_SHIFT; Err bitreich.org 70 i- hdr->flags |= hash_algo << HASH_ALGO_SHIFT; Err bitreich.org 70 i- hdr->size = BLK_HDR_SIZE; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-init_snap_hdr(struct snap_hdr *hdr) Err bitreich.org 70 i-{ Err bitreich.org 70 i- hdr->flags = (VER_MAJ << VER_MAJ_SHIFT) | VER_MIN; Err bitreich.org 70 i- hdr->size = SNAP_HDR_SIZE; Err bitreich.org 70 i- hdr->st.min_blk_size = UINT64_MAX; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-load_blk_hdr(int fd, struct blk_hdr *hdr, int *compr_algo, int *hash_algo) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint64_t v; Err bitreich.org 70 i- Err bitreich.org 70 i- read_blk_hdr(fd, hdr); Err bitreich.org 70 i- match_ver(hdr->flags); Err bitreich.org 70 i- Err bitreich.org 70 i- v = hdr->flags >> COMPR_ALGO_SHIFT; Err bitreich.org 70 i- v &= COMPR_ALGO_MASK; Err bitreich.org 70 i- *compr_algo = v; Err bitreich.org 70 i- Err bitreich.org 70 i- if (*compr_algo < 0 || *compr_algo >= NR_COMPRS) Err bitreich.org 70 i- errx(1, "unsupported compression algorithm: %d", *compr_algo); Err bitreich.org 70 i- Err bitreich.org 70 i- v = hdr->flags >> HASH_ALGO_SHIFT; Err bitreich.org 70 i- v &= HASH_ALGO_MASK; Err bitreich.org 70 i- *hash_algo = v; Err bitreich.org 70 i- Err bitreich.org 70 i- if (*hash_algo < 0 || *hash_algo >= NR_HASHES) Err bitreich.org 70 i- errx(1, "unsupported hash algorithm: %d", *hash_algo); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-load_snap_hdr(int fd, struct snap_hdr *hdr) Err bitreich.org 70 i-{ Err bitreich.org 70 i- read_snap_hdr(fd, hdr); Err bitreich.org 70 i- match_ver(hdr->flags); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-struct snap * Err bitreich.org 70 i-alloc_snap(void) Err bitreich.org 70 i-{ Err bitreich.org 70 i- struct snap *snap; Err bitreich.org 70 i- Err bitreich.org 70 i- snap = calloc(1, sizeof(*snap)); Err bitreich.org 70 i- if (snap == NULL) Err bitreich.org 70 i- err(1, "%s", __func__); Err bitreich.org 70 i- return snap; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-free_snap(struct snap *snap) Err bitreich.org 70 i-{ Err bitreich.org 70 i- free(snap); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-struct snap * Err bitreich.org 70 i-grow_snap(struct snap *snap, uint64_t nr_blk_descs) Err bitreich.org 70 i-{ Err bitreich.org 70 i- size_t size; Err bitreich.org 70 i- Err bitreich.org 70 i- if (nr_blk_descs > SIZE_MAX / sizeof(snap->blk_desc[0])) Err bitreich.org 70 i- errx(1, "%s: overflow", __func__); Err bitreich.org 70 i- size = nr_blk_descs * sizeof(snap->blk_desc[0]); Err bitreich.org 70 i- Err bitreich.org 70 i- if (size > SIZE_MAX - sizeof(*snap)) Err bitreich.org 70 i- errx(1, "%s: overflow", __func__); Err bitreich.org 70 i- size += sizeof(*snap); Err bitreich.org 70 i- Err bitreich.org 70 i- snap = realloc(snap, size); Err bitreich.org 70 i- if (snap == NULL) Err bitreich.org 70 i- err(1, "%s", __func__); Err bitreich.org 70 i- return snap; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-append_snap(int fd, struct snap_hdr *hdr, struct snap *snap) Err bitreich.org 70 i-{ Err bitreich.org 70 i- if (snap->nr_blk_descs > UINT64_MAX / BLK_DESC_SIZE) Err bitreich.org 70 i- errx(1, "%s: overflow", __func__); Err bitreich.org 70 i- snap->size = snap->nr_blk_descs * BLK_DESC_SIZE; Err bitreich.org 70 i- Err bitreich.org 70 i- if (snap->size > UINT64_MAX - SNAPSHOT_SIZE) Err bitreich.org 70 i- errx(1, "%s: overflow", __func__); Err bitreich.org 70 i- snap->size += SNAPSHOT_SIZE; Err bitreich.org 70 i- Err bitreich.org 70 i- xlseek(fd, hdr->size, SEEK_SET); Err bitreich.org 70 i- write_snap(fd, snap); Err bitreich.org 70 i- write_snap_blk_descs(fd, snap); Err bitreich.org 70 i- Err bitreich.org 70 i- if (hdr->size > UINT64_MAX - snap->size) Err bitreich.org 70 i- errx(1, "%s: overflow", __func__); Err bitreich.org 70 i- hdr->size += snap->size; Err bitreich.org 70 i- Err bitreich.org 70 i- if (hdr->nr_snaps > UINT64_MAX - 1) Err bitreich.org 70 i- errx(1, "%s: overflow", __func__); Err bitreich.org 70 i- hdr->nr_snaps++; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-/* Err bitreich.org 70 i- * The snapshot hash is calculated over the Err bitreich.org 70 i- * hash of its block descriptors. Err bitreich.org 70 i- */ Err bitreich.org 70 i-void Err bitreich.org 70 i-hash_snap(struct snap *snap, uint8_t *md, int hash_algo) Err bitreich.org 70 i-{ Err bitreich.org 70 i- struct hash_ctx ctx; Err bitreich.org 70 i- uint64_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- if (hash_init(&ctx, hash_algo, MD_SIZE) < 0) Err bitreich.org 70 i- errx(1, "hash_init failed"); Err bitreich.org 70 i- for (i = 0; i < snap->nr_blk_descs; i++) { Err bitreich.org 70 i- struct blk_desc *blk_desc; Err bitreich.org 70 i- Err bitreich.org 70 i- blk_desc = &snap->blk_desc[i]; Err bitreich.org 70 i- hash_update(&ctx, blk_desc->md, sizeof(blk_desc->md)); Err bitreich.org 70 i- } Err bitreich.org 70 i- hash_final(&ctx, md, MD_SIZE); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-/* Walk through all snapshots and call fn() on each one */ Err bitreich.org 70 i-void Err bitreich.org 70 i-walk_snap(int fd, struct snap_hdr *hdr, Err bitreich.org 70 i- int (*fn)(struct snap *, void *), void *arg) Err bitreich.org 70 i-{ Err bitreich.org 70 i- uint64_t i; Err bitreich.org 70 i- Err bitreich.org 70 i- xlseek(fd, SNAP_HDR_SIZE, SEEK_SET); Err bitreich.org 70 i- for (i = 0; i < hdr->nr_snaps; i++) { Err bitreich.org 70 i- struct snap *snap; Err bitreich.org 70 i- int ret; Err bitreich.org 70 i- Err bitreich.org 70 i- snap = alloc_snap(); Err bitreich.org 70 i- read_snap(fd, snap); Err bitreich.org 70 i- snap = grow_snap(snap, snap->nr_blk_descs); Err bitreich.org 70 i- read_snap_descs(fd, snap); Err bitreich.org 70 i- Err bitreich.org 70 i- ret = (*fn)(snap, arg); Err bitreich.org 70 i- free_snap(snap); Err bitreich.org 70 i- if (ret == WALK_STOP) Err bitreich.org 70 i- break; Err bitreich.org 70 i- } Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-uint8_t * Err bitreich.org 70 i-alloc_buf(size_t size) Err bitreich.org 70 i-{ Err bitreich.org 70 i- void *p; Err bitreich.org 70 i- Err bitreich.org 70 i- p = calloc(1, size); Err bitreich.org 70 i- if (p == NULL) Err bitreich.org 70 i- err(1, "%s", __func__); Err bitreich.org 70 i- return p; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-free_buf(uint8_t *buf) Err bitreich.org 70 i-{ Err bitreich.org 70 i- free(buf); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-read_blk(int fd, uint8_t *buf, struct blk_desc *blk_desc) Err bitreich.org 70 i-{ Err bitreich.org 70 i- ssize_t n; Err bitreich.org 70 i- Err bitreich.org 70 i- xlseek(fd, blk_desc->offset, SEEK_SET); Err bitreich.org 70 i- n = xread(fd, buf, blk_desc->size); Err bitreich.org 70 i- if (n == 0) Err bitreich.org 70 i- errx(1, "%s: unexpected EOF", __func__); Err bitreich.org 70 i- if (n != blk_desc->size) Err bitreich.org 70 i- errx(1, "%s: short read", __func__); Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-append_blk(int fd, struct blk_hdr *hdr, uint8_t *buf, struct blk_desc *blk_desc) Err bitreich.org 70 i-{ Err bitreich.org 70 i- xlseek(fd, hdr->size, SEEK_SET); Err bitreich.org 70 i- xwrite(fd, buf, blk_desc->size); Err bitreich.org 70 i- Err bitreich.org 70 i- if (hdr->size > UINT64_MAX - blk_desc->size) Err bitreich.org 70 i- errx(1, "%s: overflow", __func__); Err bitreich.org 70 i- hdr->size += blk_desc->size; Err bitreich.org 70 i-} Err bitreich.org 70 i- Err bitreich.org 70 i-void Err bitreich.org 70 i-hash_blk(uint8_t *buf, size_t size, uint8_t *md, int hash_algo) Err bitreich.org 70 i-{ Err bitreich.org 70 i- struct hash_ctx ctx; Err bitreich.org 70 i- Err bitreich.org 70 i- if (hash_init(&ctx, hash_algo, MD_SIZE) < 0) Err bitreich.org 70 i- errx(1, "hash_init failed"); Err bitreich.org 70 i- hash_update(&ctx, buf, size); Err bitreich.org 70 i- hash_final(&ctx, md, MD_SIZE); Err bitreich.org 70 i-} Err bitreich.org 70 .