comodal / hash-overlay

Binary overlay classes for message digests.

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

hash-overlay Build Status JCenter License codecov

Binary overlay classes for message digests.

Supported Message Digest Algorithms

All fixed-length message digest algorithms from providers SUN v9 and Bouncy Castle v1.56 are available. See the root source directory for a quick look of all available algorithms.

Project Goals

  • Fast hash look-ups (hashCode & equals).
  • Minimize memory usage.
    • Each Hash Object only holds a final reference to the digest byte array, resulting in a 16 byte Object. If necessary, a final offset integer is referenced as well, resulting in a 24 byte Object. To give context, wrapping it in a ByteBuffer results in a 48 byte Object.
    • Support overlaying of big or little endian byte arrays to to prevent the need to copy or reverse arrays.
    • Every effort will be made to convert existing classes to Java 10 Value Types. This will probably mean the removal of base classes and generating the same code for every value type. So do NOT extend or use anything in the systems.comodal.hash.base package. This package will not be exposed once the project is jigsaw modularized... Also, default interface method implementations are avoided because of potential Value Type performance implications (Boxing). See Minimal Value Types from John Rose and Brian Goetz.
  • Make the handling of message digests as convenient as possible without sacrificing performance.

Example Usage

byte[] message = "Hello World".getBytes(StandardCharsets.UTF_8);

HashFactory<SHA3_256> factory = SHA3_256.FACTORY;
SHA3_256 digest = factory.hash(message);

Map<Hash, byte[]> cache = new HashMap<>();
cache.put(digest, message);

byte[] nested = new byte[1024];
int offset = 42;
digest.copyHashTo(nested, offset);
SHA3_256 overlay = factory.overlay(nested, offset);

System.out.println(new String(cache.get(overlay)));

Using Bouncy Castle Provided Algorithms

// build.gradle
dependencies {
    compile 'org.bouncycastle:bcprov-jdk15on:+'
}
// Once at startup
Security.addProvider(new BouncyCastleProvider());
// ...
BLAKE2B160 digest = BLAKE2B160.FACTORY.hash(msg);

Multihash Support

  • Decode Multihash encoded digests.
  • Lookup up HashFactories by Multihash function codes.
  • Function code getters.
  • Multiformat Unsigned VarInt encoding & decoding.

See HashFactoryFnCodeFactory.java for a list of supported Multihash function codes.

See MultiHashTest.java for more complete usage examples.

// Decoding
byte[] multiHashEncoded = ... // <varint fn code><varint digest length><digest>

// Copies the digest to a new byte array with the exact digest length.
Hash hash = MultiHash.createCopy(multiHashEncoded);

// Overlay's the existing byte array.
Hash overlay = MultiHash.createOverlay(multiHashEncoded);
// Encoding
Hash hash = ...
byte[] prefix = hash.getFactory().getMultiHashPrefix();
byte[] multiHashEncoded = new byte[prefix.length + hash.getDigestLength()];
System.arraycopy(prefix, 0, multiHashEncoded, 0, prefix.length);
hash.copyTo(multiHashEncoded, prefix.length);
// VarInt Encoding/Decoding
int val = 128;
byte[] varInt = MultiHash.encodeVarInt(val);
long unsignedInt = MultiHash.decodeVarInt(varInt);
System.out.println(unsignedInt == val);
// HashFactory Lookup
int fnCode = 0xB220;
HashFactory<? extends Hash> hashFactory = MultiHash.getHashFactory(fnCode);
// Blake2b
System.out.println(hashFactory.getMessageDigest().getAlgorithm());

byte[] varIntFnCode = MultiHash.encodeVarInt(fnCode);
hashFactory = MultiHash.getHashFactory(varIntFnCode);
// Blake2b
System.out.println(hashFactory.getMessageDigest().getAlgorithm());

Generating Source

All of the algorithm specific code is generated using Mustache templates. Upon generation, any existing generated code is deleted, and new implementation code is created for every message digest algorithm found at runtime.

See the mustache module for the source that drives the code generation as well as the template resource files.

./gradlew generateSrc

About

Binary overlay classes for message digests.

License:Apache License 2.0


Languages

Language:Java 96.7%Language:HTML 3.3%