Skip to content

Commit

Permalink
Use TypedArray support in typed-binary (#129)
Browse files Browse the repository at this point in the history
Use TypedArray support in typed-binary instead of reading/writing individual bytes (closes #52)
  • Loading branch information
cyraxx authored Oct 8, 2024
1 parent 6a3e540 commit 67def7a
Show file tree
Hide file tree
Showing 9 changed files with 32 additions and 54 deletions.
5 changes: 5 additions & 0 deletions .changeset/gentle-hornets-thank.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'@trustnxt/c2pa-ts': minor
---

Use TypedArray support in typed-binary for better performance
11 changes: 4 additions & 7 deletions src/jumbf/C2PASaltBox.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,23 +8,20 @@ class C2PASaltBoxSchema extends BoxSchema<C2PASaltBox> {
if (type != C2PASaltBox.typeCode) throw new Error(`C2PASaltBox: Unexpected type ${type}`);
if (length !== 8 + 16 && length !== 8 + 32) throw new Error(`C2PASaltBox: Unexpected length ${length}`);

const salt = [];
for (let i = 8; i != length; i++) {
salt.push(input.readByte());
}
const salt = bin.u8Array(length - 8).read(input);

const box = new C2PASaltBox();
box.salt = new Uint8Array(salt);
box.salt = salt;

return box;
}

writeContent(output: bin.ISerialOutput, value: C2PASaltBox): void {
value.salt?.forEach(byte => output.writeByte(byte));
if (value.salt) output.writeSlice(value.salt);
}

measureContent(value: C2PASaltBox, measurer: bin.IMeasurer): bin.IMeasurer {
return measurer.add(value.salt ? value.salt.length : 0);
return measurer.add(value.salt?.length ?? 0);
}
}

Expand Down
9 changes: 3 additions & 6 deletions src/jumbf/CBORBox.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,13 +16,10 @@ class CBORBoxSchema extends BoxSchema<CBORBox> {
readContent(input: bin.ISerialInput, type: string, length: number): CBORBox {
if (type != CBORBox.typeCode) throw new Error(`CBORBox: Unexpected type ${type}`);

const data = [];
for (let i = 0; i < length - 8; i++) {
data.push(input.readByte());
}
const data = bin.u8Array(length - 8).read(input);

const box = new CBORBox();
box.rawContent = new Uint8Array(data);
box.rawContent = data;
try {
// If the data is tagged, store content and tag separately,
// but ignore the tag otherwise.
Expand All @@ -45,7 +42,7 @@ class CBORBoxSchema extends BoxSchema<CBORBox> {
writeContent(output: bin.ISerialOutput, value: CBORBox): void {
if (!value.rawContent) value.generateRawContent();

value.rawContent!.forEach(byte => output.writeByte(byte));
output.writeSlice(value.rawContent!);
}

measureContent(value: CBORBox, measurer: bin.IMeasurer): bin.IMeasurer {
Expand Down
11 changes: 3 additions & 8 deletions src/jumbf/CodestreamBox.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,7 @@ class CodestreamBoxSchema extends BoxSchema<CodestreamBox> {
readContent(input: bin.ISerialInput, type: string, length: number): CodestreamBox {
if (type != CodestreamBox.typeCode) throw new Error(`CodestreamBox: Unexpected type ${type}`);

const data = [];
for (let i = 0; i < length - 8; i++) {
data.push(input.readByte());
}
const data = bin.u8Array(length - 8).read(input);

const box = new CodestreamBox();
box.content = new Uint8Array(data);
Expand All @@ -18,13 +15,11 @@ class CodestreamBoxSchema extends BoxSchema<CodestreamBox> {
}

writeContent(output: bin.ISerialOutput, value: CodestreamBox): void {
if (value.content) {
value.content.forEach(byte => output.writeByte(byte));
}
if (value.content) output.writeSlice(value.content);
}

measureContent(value: CodestreamBox, measurer: bin.IMeasurer): bin.IMeasurer {
return measurer.add(value.content ? value.content.length : 0);
return measurer.add(value.content?.length ?? 0);
}
}

Expand Down
13 changes: 4 additions & 9 deletions src/jumbf/EmbeddedFileBox.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,25 +10,20 @@ class EmbeddedFileBoxSchema extends BoxSchema<EmbeddedFileBox> {
readContent(input: bin.ISerialInput, type: string, length: number): EmbeddedFileBox {
if (type != EmbeddedFileBox.typeCode) throw new Error(`EmbeddedFileBox: Unexpected type ${type}`);

const data = [];
for (let i = 0; i < length - 8; i++) {
data.push(input.readByte());
}
const data = bin.u8Array(length - 8).read(input);

const box = new EmbeddedFileBox();
box.content = new Uint8Array(data);
box.content = data;

return box;
}

writeContent(output: bin.ISerialOutput, value: EmbeddedFileBox): void {
if (value.content) {
value.content.forEach(byte => output.writeByte(byte));
}
if (value.content) output.writeSlice(value.content);
}

measureContent(value: EmbeddedFileBox, measurer: bin.IMeasurer): bin.IMeasurer {
return measurer.add(value.content ? value.content.length : 0);
return measurer.add(value.content?.length ?? 0);
}
}

Expand Down
10 changes: 2 additions & 8 deletions src/jumbf/JSONBox.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,12 +10,7 @@ class JSONBoxSchema extends BoxSchema<JSONBox> {
readContent(input: bin.ISerialInput, type: string, length: number): JSONBox {
if (type != JSONBox.typeCode) throw new Error(`JSONBox: Unexpected type ${type}`);

const payloadLength = length - 8;
const jsonBuffer = new Uint8Array(payloadLength);
for (let i = 0; i < payloadLength; i++) {
jsonBuffer[i] = input.readByte();
}
const json = new TextDecoder().decode(jsonBuffer);
const json = new TextDecoder().decode(bin.u8Array(length - 8).read(input));

const box = new JSONBox();
try {
Expand All @@ -34,8 +29,7 @@ class JSONBoxSchema extends BoxSchema<JSONBox> {
}

writeContent(output: bin.ISerialOutput, value: JSONBox): void {
const jsonBuffer = this.encodeContent(value);
for (let i = 0; i != jsonBuffer.length; i++) output.writeByte(jsonBuffer[i]);
output.writeSlice(this.encodeContent(value));
}

measureContent(value: JSONBox, measurer: bin.IMeasurer): bin.IMeasurer {
Expand Down
5 changes: 2 additions & 3 deletions src/jumbf/SuperBox.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,8 @@ class SuperBoxSchema extends BoxSchema<SuperBox> {
const box = new SuperBox();

// read raw content excluding (length, type) header
const rawContentSchema = bin.arrayOf(bin.byte, length - 8);
const buf = rawContentSchema.read(input);
box.rawContent = new Uint8Array(buf);
const rawContentSchema = bin.u8Array(length - 8);
box.rawContent = rawContentSchema.read(input);
input.skipBytes(-(length - 8));

const end = input.currentByteOffset + length - 8;
Expand Down
12 changes: 5 additions & 7 deletions src/jumbf/UUIDBox.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,25 +11,23 @@ class UUIDBoxSchema extends BoxSchema<UUIDBox> {
if (type != UUIDBox.typeCode) throw new Error(`UUIDBox: Unexpected type ${type}`);

const uuid = this.uuid.read(input);
const content = [];
for (let i = 0; i != length - 4 - 4 - 16; i++) {
content.push(input.readByte());
}
const content = bin.u8Array(length - 4 - 4 - 16).read(input);

const box = new UUIDBox();

box.uuid = uuid;
box.content = new Uint8Array(content);
box.content = content;

return box;
}

writeContent(output: bin.ISerialOutput, value: UUIDBox): void {
this.uuid.write(output, value.uuid);
value.content?.forEach(byte => output.writeByte(byte));
if (value.content) output.writeSlice(value.content);
}

measureContent(value: UUIDBox, measurer: bin.IMeasurer): bin.IMeasurer {
return measurer.add(this.uuid.measure(value.uuid).size + (value.content ? value.content.length : 0));
return measurer.add(this.uuid.measure(value.uuid).size + (value.content?.length ?? 0));
}
}

Expand Down
10 changes: 4 additions & 6 deletions src/jumbf/schemata.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,17 +32,15 @@ export const type = new JUMBFTypeCodeSchema();

// type field for UUIDs
class JUMBFUUIDSchema extends bin.Schema<Uint8Array> {
private uuid = bin.u8Array(16);

read(input: bin.ISerialInput): Uint8Array {
const uuid = [];
for (let i = 0; i != 16; i++) {
uuid.push(input.readByte());
}
return new Uint8Array(uuid);
return this.uuid.read(input);
}

write(output: bin.ISerialOutput, value: Uint8Array): void {
if (value.length != 16) throw new Error('JUMBFUUID: Invalid length');
value.forEach(byte => output.writeByte(byte));
output.writeSlice(value);
}

measure(_: Uint8Array, measurer: bin.IMeasurer = new bin.Measurer()): bin.IMeasurer {
Expand Down

0 comments on commit 67def7a

Please sign in to comment.