diff --git a/packages/as-sha256/src/hashCache.ts b/packages/as-sha256/src/hashCache.ts index 72aeea9c..601be393 100644 --- a/packages/as-sha256/src/hashCache.ts +++ b/packages/as-sha256/src/hashCache.ts @@ -19,19 +19,19 @@ export type HashCache = { */ export type HashId = number; -function toHashId(cacheIndex: number, hashIndex: number): HashId { +export function toHashId(cacheIndex: number, hashIndex: number): HashId { return (cacheIndex << 16) | hashIndex; } -function fromHashId(id: HashId): [number, number] { +export function fromHashId(id: HashId): [number, number] { return [id >> 16, id & 0xffff]; } -function getCacheIndex(id: HashId): number { +export function getCacheIndex(id: HashId): number { return id >> 16; } -function getHashIndex(id: HashId): number { +export function getHashIndex(id: HashId): number { return id & 0xffff; } @@ -46,13 +46,6 @@ export function allocHashCache(): HashCache { return out; } -export function getHash(id: HashId): Uint8Array { - const [cacheIndex, hashIndex] = fromHashId(id); - const cache = hashCaches[cacheIndex]; - const offset = hashIndex * HASH_SIZE; - return cache.cache.subarray(offset, offset + HASH_SIZE); -} - export function getCache(id: HashId): HashCache { return hashCaches[getCacheIndex(id)]; } @@ -65,7 +58,7 @@ export function incrementNext(cache: HashCache): number { const out = cache.next; cache.used.add(out); // eslint-disable-next-line no-empty - while (cache.used.has(cache.next++)) {} + while (cache.used.has(++cache.next)) {} return out; } @@ -134,6 +127,13 @@ export function cloneHashId(source: HashId, target: HashId): void { cacheTarget[offsetTarget++] = cacheSource[offsetSource++]; } +export function getHash(id: HashId): Uint8Array { + const [cacheIndex, hashIndex] = fromHashId(id); + const cache = hashCaches[cacheIndex]; + const offset = hashIndex * HASH_SIZE; + return cache.cache.subarray(offset, offset + HASH_SIZE); +} + export function getHashObject(id: HashId): HashObject { const {cache} = getCache(id); let offset = getCacheOffset(id); diff --git a/packages/as-sha256/test/unit/hashCache.test.ts b/packages/as-sha256/test/unit/hashCache.test.ts index 5182937d..9dc48237 100644 --- a/packages/as-sha256/test/unit/hashCache.test.ts +++ b/packages/as-sha256/test/unit/hashCache.test.ts @@ -1,7 +1,29 @@ import {expect} from "chai"; -import {allocHashId, digest2Bytes32, digest64HashIds, freeHashId, getHash} from "../../src"; +import {CACHE_HASH_SIZE, allocHashId, digest2Bytes32, digest64HashIds, freeHashId, getCache, getHash, getHashIndex} from "../../src"; describe("hash cache", () => { + it("should allocate and free hash ids", () => { + let id = allocHashId(); + const hashIndex = getHashIndex(id); + if (hashIndex >= CACHE_HASH_SIZE / 2) { + console.warn("unreachable"); + return; + } + + const ids = [id]; + for (let i = 0; i < CACHE_HASH_SIZE - hashIndex; i++) { + ids.push(allocHashId()); + } + + expect(getCache(ids[0]).used.size).to.equal(CACHE_HASH_SIZE); + + for (const id of ids) { + freeHashId(id); + } + + expect(getCache(ids[0]).used.size).to.equal(Math.max(CACHE_HASH_SIZE - ids.length, 0)); + }); + it("should properly hash many items", function () { this.timeout(0);