Checkpoint
This commit is contained in:
110
ui/src/util.ts
Normal file
110
ui/src/util.ts
Normal file
@@ -0,0 +1,110 @@
|
||||
export const base64ToBytes = (b64: string): Uint8Array => {
|
||||
const binaryString = atob(b64);
|
||||
const bytes = new Uint8Array(binaryString.length);
|
||||
for (let i = 0; i < binaryString.length; i++) {
|
||||
bytes[i] = binaryString.charCodeAt(i);
|
||||
}
|
||||
return bytes;
|
||||
}
|
||||
|
||||
export const bytesToBase64 = (buf: Uint8Array): string => {
|
||||
const bytes: string[] = new Array(buf.length);
|
||||
for (let i = 0; i < buf.length; i++) {
|
||||
bytes[i] = String.fromCharCode(buf[i]);
|
||||
}
|
||||
return btoa(bytes.join(''));
|
||||
}
|
||||
|
||||
/**
|
||||
* Do semi constant time comparison of two Uint8Arrays to prevent timing attacks.
|
||||
* Returns true if the arrays are equal, false otherwise.
|
||||
*
|
||||
* Note: This is not truly constant time, but it is designed to take the same amount of time regardless of where the first difference is.
|
||||
* It will still take longer for longer arrays, but it will not short-circuit on the first difference.
|
||||
*/
|
||||
export const constantTimeEqual = (a: Uint8Array, b: Uint8Array): boolean => {
|
||||
if (a.length !== b.length) return false;
|
||||
|
||||
let result = 0;
|
||||
for (let i = 0; i < a.length; i++) {
|
||||
result |= a[i] ^ b[i];
|
||||
}
|
||||
return result === 0;
|
||||
}
|
||||
|
||||
/* BufferReader is a utility class for reading and writing binary data from a Uint8Array buffer.
|
||||
* It maintains an internal offset and length to track the current position in the buffer. It
|
||||
* provides methods for reading unsigned integers in little-endian format, as well as arbitrary
|
||||
* byte arrays. It also allows writing unsigned integers back into the buffer. This class is
|
||||
* useful for parsing and constructing binary protocols.
|
||||
*/
|
||||
export class BufferReader {
|
||||
protected buffer: Uint8Array;
|
||||
protected offset: number = 0;
|
||||
public length: number = 0;
|
||||
|
||||
constructor(buffer: Uint8Array) {
|
||||
this.buffer = new Uint8Array(buffer.length);
|
||||
for (let i = 0; i < buffer.length; i++) {
|
||||
this.buffer[i] = buffer[i];
|
||||
}
|
||||
this.length = buffer.length;
|
||||
}
|
||||
|
||||
public reset(buffer: Uint8Array) {
|
||||
this.buffer = new Uint8Array(buffer.length);
|
||||
for (let i = 0; i < buffer.length; i++) {
|
||||
this.buffer[i] = buffer[i];
|
||||
}
|
||||
this.offset = 0;
|
||||
this.length = buffer.length;
|
||||
}
|
||||
|
||||
public readUint8(): number {
|
||||
const value = this.buffer[this.offset];
|
||||
this.offset++;
|
||||
this.length--;
|
||||
return value;
|
||||
}
|
||||
|
||||
public readUint16LE(): number {
|
||||
const value = this.buffer[this.offset] | (this.buffer[this.offset + 1] << 8);
|
||||
this.offset += 2;
|
||||
this.length -= 2;
|
||||
return value;
|
||||
}
|
||||
|
||||
public readUint32LE(): number {
|
||||
const value = this.buffer[this.offset] |
|
||||
(this.buffer[this.offset + 1] << 8) |
|
||||
(this.buffer[this.offset + 2] << 16) |
|
||||
(this.buffer[this.offset + 3] << 24);
|
||||
this.offset += 4;
|
||||
this.length -= 4;
|
||||
return value;
|
||||
}
|
||||
|
||||
public readBytes(size?: number): Uint8Array {
|
||||
size ||= (this.buffer.length - this.offset);
|
||||
const value = this.buffer.slice(this.offset, this.offset + size);
|
||||
this.offset += size;
|
||||
this.length -= size;
|
||||
return value;
|
||||
}
|
||||
|
||||
public writeUint16LE(value: number): void {
|
||||
this.buffer[this.offset] = value & 0xFF;
|
||||
this.buffer[this.offset + 1] = (value >> 8) & 0xFF;
|
||||
this.offset += 2;
|
||||
this.length += 2;
|
||||
}
|
||||
|
||||
public writeUint32LE(value: number): void {
|
||||
this.buffer[this.offset] = value & 0xFF;
|
||||
this.buffer[this.offset + 1] = (value >> 8) & 0xFF;
|
||||
this.buffer[this.offset + 2] = (value >> 16) & 0xFF;
|
||||
this.buffer[this.offset + 3] = (value >> 24) & 0xFF;
|
||||
this.offset += 4;
|
||||
this.length += 4;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user