refactor reader and writer.
This commit is contained in:
parent
7e4ac9b0ed
commit
f0c73f41a6
@ -31,6 +31,37 @@ function BufferReader(data, zeroCopy) {
|
||||
this.stack = [];
|
||||
}
|
||||
|
||||
/**
|
||||
* Get total size of passed-in Buffer.
|
||||
* @returns {Buffer}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.getSize = function getSize() {
|
||||
return this.data.length;
|
||||
};
|
||||
|
||||
/**
|
||||
* Calculate number of bytes left to read.
|
||||
* @returns {Number}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.left = function left() {
|
||||
assert(this.offset <= this.data.length);
|
||||
return this.data.length - this.offset;
|
||||
};
|
||||
|
||||
/**
|
||||
* Seek to a position to read from by offset.
|
||||
* @param {Number} off - Offset (positive or negative).
|
||||
*/
|
||||
|
||||
BufferReader.prototype.seek = function seek(off) {
|
||||
assert(this.offset + off >= 0);
|
||||
assert(this.offset + off <= this.data.length);
|
||||
this.offset += off;
|
||||
return off;
|
||||
};
|
||||
|
||||
/**
|
||||
* Mark the current starting position.
|
||||
*/
|
||||
@ -384,167 +415,6 @@ BufferReader.prototype.read53BE = function read53BE() {
|
||||
return this.read64NBE(true);
|
||||
};
|
||||
|
||||
/**
|
||||
* Read N bytes (will do a fast slice if zero copy).
|
||||
* @param {Number} size
|
||||
* @returns {Buffer}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readBytes = function readBytes(size) {
|
||||
var ret;
|
||||
|
||||
assert(size >= 0);
|
||||
assert(this.offset + size <= this.data.length);
|
||||
|
||||
if (this.zeroCopy) {
|
||||
ret = this.data.slice(this.offset, this.offset + size);
|
||||
} else {
|
||||
ret = new Buffer(size);
|
||||
this.data.copy(ret, 0, this.offset, this.offset + size);
|
||||
}
|
||||
|
||||
this.offset += size;
|
||||
|
||||
return ret;
|
||||
};
|
||||
|
||||
/**
|
||||
* Read a string.
|
||||
* @param {String} enc - Any buffer-supported encoding.
|
||||
* @param {Number} size
|
||||
* @returns {String}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readString = function readString(enc, size) {
|
||||
var ret;
|
||||
assert(size >= 0);
|
||||
assert(this.offset + size <= this.data.length);
|
||||
ret = this.data.toString(enc, this.offset, this.offset + size);
|
||||
this.offset += size;
|
||||
return ret;
|
||||
};
|
||||
|
||||
/**
|
||||
* Read a 32-byte hash.
|
||||
* @param {String} enc - `"hex"` or `null`.
|
||||
* @returns {Hash|Buffer}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readHash = function readHash(enc) {
|
||||
if (enc)
|
||||
return this.readString(enc, 32);
|
||||
return this.readBytes(32);
|
||||
};
|
||||
|
||||
/**
|
||||
* Read string of a varint length.
|
||||
* @param {String} enc - Any buffer-supported encoding.
|
||||
* @returns {String}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readVarString = function readVarString(enc) {
|
||||
return this.readString(enc, this.readVarint());
|
||||
};
|
||||
|
||||
/**
|
||||
* Read a varint number of bytes (will do a fast slice if zero copy).
|
||||
* @returns {Buffer}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readVarBytes = function readVarBytes() {
|
||||
return this.readBytes(this.readVarint());
|
||||
};
|
||||
|
||||
/**
|
||||
* Read a null-terminated string.
|
||||
* @param {String} enc - Any buffer-supported encoding.
|
||||
* @returns {String}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readNullString = function readNullString(enc) {
|
||||
var i, ret;
|
||||
assert(this.offset + 1 <= this.data.length);
|
||||
for (i = this.offset; i < this.data.length; i++) {
|
||||
if (this.data[i] === 0)
|
||||
break;
|
||||
}
|
||||
assert(i !== this.data.length);
|
||||
ret = this.readString(enc, i - this.offset);
|
||||
this.offset = i + 1;
|
||||
return ret;
|
||||
};
|
||||
|
||||
/**
|
||||
* Read a varint.
|
||||
* @param {Boolean?} big - Whether to read as a big number.
|
||||
* @returns {Number}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readVarint = function readVarint(big) {
|
||||
var result;
|
||||
assert(this.offset + 1 <= this.data.length);
|
||||
result = utils.readVarint(this.data, this.offset, big);
|
||||
assert(result.off <= this.data.length);
|
||||
assert(result.r >= 0);
|
||||
this.offset = result.off;
|
||||
return result.r;
|
||||
};
|
||||
|
||||
/**
|
||||
* Calculate number of bytes left to read.
|
||||
* @returns {Number}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.left = function left() {
|
||||
assert(this.offset <= this.data.length);
|
||||
return this.data.length - this.offset;
|
||||
};
|
||||
|
||||
/**
|
||||
* Get total size of passed-in Buffer.
|
||||
* @returns {Buffer}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.getSize = function getSize() {
|
||||
return this.data.length;
|
||||
};
|
||||
|
||||
/**
|
||||
* Seek to a position to read from by offset.
|
||||
* @param {Number} off - Offset (positive or negative).
|
||||
*/
|
||||
|
||||
BufferReader.prototype.seek = function seek(off) {
|
||||
assert(this.offset + off >= 0);
|
||||
assert(this.offset + off <= this.data.length);
|
||||
this.offset += off;
|
||||
return off;
|
||||
};
|
||||
|
||||
/**
|
||||
* Create a checksum from the last start position.
|
||||
* @returns {Number} Checksum.
|
||||
*/
|
||||
|
||||
BufferReader.prototype.createChecksum = function createChecksum() {
|
||||
var start = this.stack[this.stack.length - 1] || 0;
|
||||
var data = this.data.slice(start, this.offset);
|
||||
return utils.readU32(utils.checksum(data), 0);
|
||||
};
|
||||
|
||||
/**
|
||||
* Verify a 4-byte checksum against a calculated checksum.
|
||||
* @returns {Number} checksum
|
||||
* @throws on bad checksum
|
||||
*/
|
||||
|
||||
BufferReader.prototype.verifyChecksum = function verifyChecksum() {
|
||||
var chk = this.createChecksum();
|
||||
var checksum = this.readU32();
|
||||
assert(chk === checksum, 'Checksum mismatch.');
|
||||
return checksum;
|
||||
};
|
||||
|
||||
/**
|
||||
* Read float le.
|
||||
* @returns {Number}
|
||||
@ -597,6 +467,136 @@ BufferReader.prototype.readDoubleBE = function readDoubleBE() {
|
||||
return ret;
|
||||
};
|
||||
|
||||
/**
|
||||
* Read a varint.
|
||||
* @param {Boolean?} big - Whether to read as a big number.
|
||||
* @returns {Number}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readVarint = function readVarint(big) {
|
||||
var result;
|
||||
assert(this.offset + 1 <= this.data.length);
|
||||
result = utils.readVarint(this.data, this.offset, big);
|
||||
assert(result.off <= this.data.length);
|
||||
assert(result.r >= 0);
|
||||
this.offset = result.off;
|
||||
return result.r;
|
||||
};
|
||||
|
||||
/**
|
||||
* Read N bytes (will do a fast slice if zero copy).
|
||||
* @param {Number} size
|
||||
* @returns {Buffer}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readBytes = function readBytes(size) {
|
||||
var ret;
|
||||
|
||||
assert(size >= 0);
|
||||
assert(this.offset + size <= this.data.length);
|
||||
|
||||
if (this.zeroCopy) {
|
||||
ret = this.data.slice(this.offset, this.offset + size);
|
||||
} else {
|
||||
ret = new Buffer(size);
|
||||
this.data.copy(ret, 0, this.offset, this.offset + size);
|
||||
}
|
||||
|
||||
this.offset += size;
|
||||
|
||||
return ret;
|
||||
};
|
||||
|
||||
/**
|
||||
* Read a varint number of bytes (will do a fast slice if zero copy).
|
||||
* @returns {Buffer}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readVarBytes = function readVarBytes() {
|
||||
return this.readBytes(this.readVarint());
|
||||
};
|
||||
|
||||
/**
|
||||
* Read a string.
|
||||
* @param {String} enc - Any buffer-supported encoding.
|
||||
* @param {Number} size
|
||||
* @returns {String}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readString = function readString(enc, size) {
|
||||
var ret;
|
||||
assert(size >= 0);
|
||||
assert(this.offset + size <= this.data.length);
|
||||
ret = this.data.toString(enc, this.offset, this.offset + size);
|
||||
this.offset += size;
|
||||
return ret;
|
||||
};
|
||||
|
||||
/**
|
||||
* Read a 32-byte hash.
|
||||
* @param {String} enc - `"hex"` or `null`.
|
||||
* @returns {Hash|Buffer}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readHash = function readHash(enc) {
|
||||
if (enc)
|
||||
return this.readString(enc, 32);
|
||||
return this.readBytes(32);
|
||||
};
|
||||
|
||||
/**
|
||||
* Read string of a varint length.
|
||||
* @param {String} enc - Any buffer-supported encoding.
|
||||
* @returns {String}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readVarString = function readVarString(enc) {
|
||||
return this.readString(enc, this.readVarint());
|
||||
};
|
||||
|
||||
/**
|
||||
* Read a null-terminated string.
|
||||
* @param {String} enc - Any buffer-supported encoding.
|
||||
* @returns {String}
|
||||
*/
|
||||
|
||||
BufferReader.prototype.readNullString = function readNullString(enc) {
|
||||
var i, ret;
|
||||
assert(this.offset + 1 <= this.data.length);
|
||||
for (i = this.offset; i < this.data.length; i++) {
|
||||
if (this.data[i] === 0)
|
||||
break;
|
||||
}
|
||||
assert(i !== this.data.length);
|
||||
ret = this.readString(enc, i - this.offset);
|
||||
this.offset = i + 1;
|
||||
return ret;
|
||||
};
|
||||
|
||||
/**
|
||||
* Create a checksum from the last start position.
|
||||
* @returns {Number} Checksum.
|
||||
*/
|
||||
|
||||
BufferReader.prototype.createChecksum = function createChecksum() {
|
||||
var start = this.stack[this.stack.length - 1] || 0;
|
||||
var data = this.data.slice(start, this.offset);
|
||||
return utils.readU32(utils.checksum(data), 0);
|
||||
};
|
||||
|
||||
/**
|
||||
* Verify a 4-byte checksum against a calculated checksum.
|
||||
* @returns {Number} checksum
|
||||
* @throws on bad checksum
|
||||
*/
|
||||
|
||||
BufferReader.prototype.verifyChecksum = function verifyChecksum() {
|
||||
var chk = this.createChecksum();
|
||||
var checksum = this.readU32();
|
||||
assert(chk === checksum, 'Checksum mismatch.');
|
||||
return checksum;
|
||||
};
|
||||
|
||||
/*
|
||||
* Expose
|
||||
*/
|
||||
|
||||
@ -86,6 +86,24 @@ BufferWriter.prototype.render = function render(keep) {
|
||||
return data;
|
||||
};
|
||||
|
||||
/**
|
||||
* Get size of data written so far.
|
||||
* @returns {Number}
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.getSize = function getSize() {
|
||||
return this.written;
|
||||
};
|
||||
|
||||
/*
|
||||
* Seek to relative offset.
|
||||
* @param {Number} offset
|
||||
*/
|
||||
|
||||
// BufferWriter.prototype.seek = function seek(offset) {
|
||||
// this.data.push(['seek', offset]);
|
||||
// };
|
||||
|
||||
/**
|
||||
* Destroy the buffer writer. Remove references to `data`.
|
||||
*/
|
||||
@ -236,6 +254,61 @@ BufferWriter.prototype.write64BE = function write64BE(value) {
|
||||
this.data.push(['64be', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write float le.
|
||||
* @param {Number} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.writeFloat = function writeFloat(value) {
|
||||
assert(typeof value === 'number');
|
||||
this.written += 4;
|
||||
this.data.push(['f', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write float be.
|
||||
* @param {Number} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.writeFloatBE = function writeFloatBE(value) {
|
||||
assert(typeof value === 'number');
|
||||
this.written += 4;
|
||||
this.data.push(['fbe', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write double le.
|
||||
* @param {Number} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.writeDouble = function writeDouble(value) {
|
||||
assert(typeof value === 'number');
|
||||
this.written += 8;
|
||||
this.data.push(['d', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write double be.
|
||||
* @param {Number} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.writeDoubleBE = function writeDoubleBE(value) {
|
||||
assert(typeof value === 'number');
|
||||
this.written += 8;
|
||||
this.data.push(['dbe', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write a varint.
|
||||
* @param {BN|Number} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.writeVarint = function writeVarint(value) {
|
||||
assert(value >= 0);
|
||||
this.written += utils.sizeVarint(value);
|
||||
this.data.push(['varint', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write bytes.
|
||||
* @param {Buffer} value
|
||||
@ -247,12 +320,15 @@ BufferWriter.prototype.writeBytes = function writeBytes(value) {
|
||||
};
|
||||
|
||||
/**
|
||||
* Get size of data written so far.
|
||||
* @returns {Number}
|
||||
* Write bytes with a varint length before them.
|
||||
* @param {Buffer} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.getSize = function getSize() {
|
||||
return this.written;
|
||||
BufferWriter.prototype.writeVarBytes = function writeVarBytes(value) {
|
||||
this.written += utils.sizeVarint(value.length);
|
||||
this.written += value.length;
|
||||
this.data.push(['varint', value.length]);
|
||||
this.data.push(['bytes', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
@ -298,18 +374,6 @@ BufferWriter.prototype.writeVarString = function writeVarString(value, enc) {
|
||||
this.data.push(['str', value, enc]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write bytes with a varint length before them.
|
||||
* @param {Buffer} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.writeVarBytes = function writeVarBytes(value) {
|
||||
this.written += utils.sizeVarint(value.length);
|
||||
this.written += value.length;
|
||||
this.data.push(['varint', value.length]);
|
||||
this.data.push(['bytes', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write a null-terminated string.
|
||||
* @param {String|Buffer}
|
||||
@ -321,17 +385,6 @@ BufferWriter.prototype.writeNullString = function writeNullString(value, enc) {
|
||||
this.writeU8(0);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write a varint.
|
||||
* @param {BN|Number} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.writeVarint = function writeVarint(value) {
|
||||
assert(value >= 0);
|
||||
this.written += utils.sizeVarint(value);
|
||||
this.data.push(['varint', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Calculate and write a checksum for the data written so far.
|
||||
*/
|
||||
@ -365,59 +418,6 @@ BufferWriter.prototype.fill = function fill(value, size) {
|
||||
// this.data.push(['fill', value, size]);
|
||||
// };
|
||||
|
||||
/*
|
||||
* Seek to relative offset.
|
||||
* @param {Number} offset
|
||||
*/
|
||||
|
||||
// BufferWriter.prototype.seek = function seek(offset) {
|
||||
// this.data.push(['seek', offset]);
|
||||
// };
|
||||
|
||||
/**
|
||||
* Write float le.
|
||||
* @param {Number} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.writeFloat = function writeFloat(value) {
|
||||
assert(typeof value === 'number');
|
||||
this.written += 4;
|
||||
this.data.push(['f', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write float be.
|
||||
* @param {Number} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.writeFloatBE = function writeFloatBE(value) {
|
||||
assert(typeof value === 'number');
|
||||
this.written += 4;
|
||||
this.data.push(['fbe', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write double le.
|
||||
* @param {Number} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.writeDouble = function writeDouble(value) {
|
||||
assert(typeof value === 'number');
|
||||
this.written += 8;
|
||||
this.data.push(['d', value]);
|
||||
};
|
||||
|
||||
/**
|
||||
* Write double be.
|
||||
* @param {Number} value
|
||||
*/
|
||||
|
||||
BufferWriter.prototype.writeDoubleBE = function writeDoubleBE(value) {
|
||||
assert(typeof value === 'number');
|
||||
this.written += 8;
|
||||
this.data.push(['dbe', value]);
|
||||
};
|
||||
|
||||
/*
|
||||
* Expose
|
||||
*/
|
||||
|
||||
Loading…
Reference in New Issue
Block a user