Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
94 changes: 46 additions & 48 deletions assembly/buffer/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,28 +7,28 @@ export class Buffer extends Uint8Array {
super(size);
}

public static alloc(size: i32): Buffer {
static alloc(size: i32): Buffer {
return new Buffer(size);
}

@unsafe public static allocUnsafe(size: i32): Buffer {
@unsafe static allocUnsafe(size: i32): Buffer {
// Node throws an error if size is less than 0
if (u32(size) > BLOCK_MAXSIZE) throw new RangeError(E_INVALIDLENGTH);
if (<u32>size > BLOCK_MAXSIZE) throw new RangeError(E_INVALIDLENGTH);
let buffer = __alloc(size, idof<ArrayBuffer>());
// This retains the pointer to the result Buffer.
let result = changetype<Buffer>(__alloc(offsetof<Buffer>(), idof<Buffer>()));
result.data = changetype<ArrayBuffer>(buffer);
result.dataStart = changetype<usize>(buffer);
result.dataStart = buffer;
result.dataLength = size;
return result;
}

public static isBuffer<T>(value: T): bool {
static isBuffer<T>(value: T): bool {
return value instanceof Buffer;
}

// Adapted from https://github.com/AssemblyScript/assemblyscript/blob/master/std/assembly/typedarray.ts
public subarray(begin: i32 = 0, end: i32 = 0x7fffffff): Buffer {
subarray(begin: i32 = 0, end: i32 = 0x7fffffff): Buffer {
var len = <i32>this.dataLength;
begin = begin < 0 ? max(len + begin, 0) : min(begin, len);
end = end < 0 ? max(len + end, 0) : min(end, len);
Expand Down Expand Up @@ -69,7 +69,7 @@ export class Buffer extends Uint8Array {

readInt16BE(offset: i32 = 0): i16 {
if (i32(offset < 0) | i32(<u32>offset + 2 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
return bswap<i16>(load<i16>(this.dataStart + <usize>offset));
return bswap(load<i16>(this.dataStart + <usize>offset));
}

readUInt16LE(offset: i32 = 0): u16 {
Expand All @@ -79,7 +79,7 @@ export class Buffer extends Uint8Array {

readUInt16BE(offset: i32 = 0): u16 {
if (i32(offset < 0) | i32(<u32>offset + 2 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
return bswap<u16>(load<u16>(this.dataStart + <usize>offset));
return bswap(load<u16>(this.dataStart + <usize>offset));
}

writeInt16LE(value: i16, offset: i32 = 0): i32 {
Expand All @@ -90,7 +90,7 @@ export class Buffer extends Uint8Array {

writeInt16BE(value: i16, offset: i32 = 0): i32 {
if (i32(offset < 0) | i32(<u32>offset + 2 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
store<i16>(this.dataStart + offset, bswap<i16>(value));
store<i16>(this.dataStart + offset, bswap(value));
return offset + 2;
}

Expand All @@ -102,7 +102,7 @@ export class Buffer extends Uint8Array {

writeUInt16BE(value: u16, offset: i32 = 0): i32 {
if (i32(offset < 0) | i32(<u32>offset + 2 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
store<u16>(this.dataStart + offset, bswap<u16>(value));
store<u16>(this.dataStart + offset, bswap(value));
return offset + 2;
}

Expand All @@ -113,7 +113,7 @@ export class Buffer extends Uint8Array {

readInt32BE(offset: i32 = 0): i32 {
if (i32(offset < 0) | i32(<u32>offset + 4 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
return bswap<i32>(load<i32>(this.dataStart + <usize>offset));
return bswap(load<i32>(this.dataStart + <usize>offset));
}

readUInt32LE(offset: i32 = 0): u32 {
Expand All @@ -123,7 +123,7 @@ export class Buffer extends Uint8Array {

readUInt32BE(offset: i32 = 0): u32 {
if (i32(offset < 0) | i32(<u32>offset + 4 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
return bswap<u32>(load<u32>(this.dataStart + <usize>offset));
return bswap(load<u32>(this.dataStart + <usize>offset));
}

writeInt32LE(value: i32, offset: i32 = 0): i32 {
Expand All @@ -134,7 +134,7 @@ export class Buffer extends Uint8Array {

writeInt32BE(value: i32, offset: i32 = 0): i32 {
if (i32(offset < 0) | i32(<u32>offset + 4 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
store<i32>(this.dataStart + offset, bswap<i32>(value));
store<i32>(this.dataStart + offset, bswap(value));
return offset + 4;
}

Expand All @@ -146,7 +146,7 @@ export class Buffer extends Uint8Array {

writeUInt32BE(value: u32, offset: i32 = 0): i32 {
if (i32(offset < 0) | i32(<u32>offset + 4 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
store<u32>(this.dataStart + offset, bswap<u32>(value));
store<u32>(this.dataStart + offset, bswap(value));
return offset + 4;
}

Expand All @@ -157,7 +157,7 @@ export class Buffer extends Uint8Array {

readFloatBE(offset: i32 = 0): f32 {
if (i32(offset < 0) | i32(<u32>offset + 4 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
return reinterpret<f32>(bswap<i32>(load<i32>(this.dataStart + <usize>offset)));
return reinterpret<f32>(bswap(load<i32>(this.dataStart + <usize>offset)));
}

writeFloatLE(value: f32, offset: i32 = 0): i32 {
Expand All @@ -168,7 +168,7 @@ export class Buffer extends Uint8Array {

writeFloatBE(value: f32, offset: i32 = 0): i32 {
if (i32(offset < 0) | i32(<u32>offset + 4 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
store<i32>(this.dataStart + offset, bswap<i32>(reinterpret<i32>(value)));
store<i32>(this.dataStart + offset, bswap(reinterpret<i32>(value)));
return offset + 4;
}

Expand All @@ -179,7 +179,7 @@ export class Buffer extends Uint8Array {

readBigInt64BE(offset: i32 = 0): i64 {
if (i32(offset < 0) | i32(<u32>offset + 8 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
return bswap<i64>(load<i64>(this.dataStart + <usize>offset));
return bswap(load<i64>(this.dataStart + <usize>offset));
}

readBigUInt64LE(offset: i32 = 0): u64 {
Expand All @@ -189,7 +189,7 @@ export class Buffer extends Uint8Array {

readBigUInt64BE(offset: i32 = 0): u64 {
if (i32(offset < 0) | i32(<u32>offset + 8 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
return bswap<u64>(load<u64>(this.dataStart + <usize>offset));
return bswap(load<u64>(this.dataStart + <usize>offset));
}

writeBigInt64LE(value: i64, offset: i32 = 0): i32 {
Expand All @@ -200,7 +200,7 @@ export class Buffer extends Uint8Array {

writeBigInt64BE(value: i64, offset: i32 = 0): i32 {
if (i32(offset < 0) | i32(<u32>offset + 8 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
store<i64>(this.dataStart + offset, bswap<i64>(value));
store<i64>(this.dataStart + offset, bswap(value));
return offset + 8;
}

Expand All @@ -212,7 +212,7 @@ export class Buffer extends Uint8Array {

writeBigUInt64BE(value: u64, offset: i32 = 0): i32 {
if (i32(offset < 0) | i32(<u32>offset + 8 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
store<u64>(this.dataStart + offset, bswap<u64>(value));
store<u64>(this.dataStart + offset, bswap(value));
return offset + 8;
}

Expand All @@ -223,7 +223,7 @@ export class Buffer extends Uint8Array {

readDoubleBE(offset: i32 = 0): f64 {
if (i32(offset < 0) | i32(<u32>offset + 8 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
return reinterpret<f64>(bswap<i64>(load<i64>(this.dataStart + <usize>offset)));
return reinterpret<f64>(bswap(load<i64>(this.dataStart + <usize>offset)));
}

writeDoubleLE(value: f64, offset: i32 = 0): i32 {
Expand All @@ -234,7 +234,7 @@ export class Buffer extends Uint8Array {

writeDoubleBE(value: f64, offset: i32 = 0): i32 {
if (i32(offset < 0) | i32(<u32>offset + 8 > this.dataLength)) throw new RangeError(E_INDEXOUTOFRANGE);
store<i64>(this.dataStart + offset, bswap<i64>(reinterpret<i64>(value)));
store<i64>(this.dataStart + offset, bswap(reinterpret<i64>(value)));
return offset + 8;
}

Expand All @@ -245,33 +245,33 @@ export class Buffer extends Uint8Array {
let dataStart = this.dataStart;
dataLength += dataStart;
while (dataStart < dataLength) {
store<u16>(dataStart, bswap<u16>(load<u16>(dataStart)));
store<u16>(dataStart, bswap(load<u16>(dataStart)));
dataStart += 2;
}
return this;
}

swap32(): Buffer {
let dataLength = this.dataLength;
// Make sure dataLength is divisible by 4
if (dataLength & 3) throw new RangeError(E_INVALIDLENGTH);
let dataStart = this.dataStart;
dataLength += dataStart;
while (dataStart < dataLength) {
store<u32>(dataStart, bswap<u32>(load<u32>(dataStart)));
store<u32>(dataStart, bswap(load<u32>(dataStart)));
dataStart += 4;
}
return this;
}

swap64(): Buffer {
let dataLength = this.dataLength;
// Make sure dataLength is divisible by 8
if (dataLength & 7) throw new RangeError(E_INVALIDLENGTH);
let dataStart = this.dataStart;
dataLength += dataStart;
while (dataStart < dataLength) {
store<u64>(dataStart, bswap<u64>(load<u64>(dataStart)));
store<u64>(dataStart, bswap(load<u64>(dataStart)));
dataStart += 8;
}
return this;
Expand All @@ -280,29 +280,20 @@ export class Buffer extends Uint8Array {

export namespace Buffer {
export namespace HEX {
/** Calculates the two char combination from the byte. */
@inline export function charsFromByte(byte: u32): u32 {
let top = (byte >>> 4) & 0xF;
let bottom = (0xF & byte);
top += select(0x57, 0x30, top > 9);
bottom += select(0x57, 0x30, bottom > 9);
return (bottom << 16) | top;
}

/** Calculates the byte length of the specified string when encoded as HEX. */
export function byteLength(str: string): i32 {
let ptr = changetype<usize>(str);
let byteCount = changetype<BLOCK>(changetype<usize>(str) - BLOCK_OVERHEAD).rtSize;
let length = byteCount >> 2;
// The string length must be even because the bytes come in pairs of characters two wide
if (byteCount & 0x3) return 0; // encoding fails and returns an empty ArrayBuffer
if (byteCount & 3) return 0; // encoding fails and returns an empty ArrayBuffer

byteCount += ptr;
while (ptr < byteCount) {
var char = load<u16>(ptr);
if ( ((char - 0x30) <= 0x9)
|| ((char - 0x61) <= 0x5)
|| ((char - 0x41) <= 0x5)) {
if ( ((char - 0x30) <= 9)
|| ((char - 0x61) <= 5)
|| ((char - 0x41) <= 5)) {
ptr += 2;
continue;
} else {
Expand All @@ -325,15 +316,14 @@ export namespace Buffer {
let b: u32 = 0;
let outChar = 0;
for (let i: usize = 0; ptr < byteEnd; i++) {
let odd = i & 1;
if (odd) {
if (i & 1) {
outChar <<= 4;
b >>>= 16;
if ((b - 0x30) <= 9) {
outChar |= b - 0x30;
} else if ((b - 0x61) <= 0x5) {
} else if ((b - 0x61) <= 5) {
outChar |= b - 0x57;
} else if (b - 0x41 <= 0x5) {
} else if (b - 0x41 <= 5) {
outChar |= b - 0x37;
}
store<u8>(result + (i >> 1), <u8>(outChar & 0xFF));
Expand All @@ -344,9 +334,9 @@ export namespace Buffer {
let c = b & 0xFF;
if ((c - 0x30) <= 9) {
outChar |= c - 0x30;
} else if ((c - 0x61) <= 0x5) {
} else if ((c - 0x61) <= 5) {
outChar |= c - 0x57;
} else if (c - 0x41 <= 0x5) {
} else if (c - 0x41 <= 5) {
outChar |= c - 0x37;
}
}
Expand All @@ -368,12 +358,20 @@ export namespace Buffer {

// loop over each byte and store a `u32` for each one
while (ptr < inputByteLength) {
store<u32>(result + i, charsFromByte(<u32>load<u8>(ptr)));
store<u32>(result + i, charsFromByte(<u32>load<u8>(ptr++)));
i += 4;
ptr++;
}

return changetype<string>(result);
}

/** Calculates the two char combination from the byte. */
@inline function charsFromByte(byte: u32): u32 {
let hi = (byte >>> 4) & 0xF;
let lo = byte & 0xF;
hi += select(0x57, 0x30, hi > 9);
lo += select(0x57, 0x30, lo > 9);
return (lo << 16) | hi;
}
}
}