var b = Object.defineProperty;
var a = (r, t) => b(r, "name", { value: t, configurable: !0 });
import { varint32write as l, varint64write as o, varint64read as d, varint32read as k } from "./google/varint.js";
import { assertUInt32 as w, assertInt32 as f, assertFloat32 as p } from "./private/assert.js";
import { protoInt64 as n } from "./proto-int64.js";
var h;
(function(r) {
  r[r.Varint = 0] = "Varint", r[r.Bit64 = 1] = "Bit64", r[r.LengthDelimited = 2] = "LengthDelimited", r[r.StartGroup = 3] = "StartGroup", r[r.EndGroup = 4] = "EndGroup", r[r.Bit32 = 5] = "Bit32";
})(h || (h = {}));
class E {
  static {
    a(this, "BinaryWriter");
  }
  constructor(t) {
    this.stack = [], this.textEncoder = t ?? new TextEncoder(), this.chunks = [], this.buf = [];
  }
  /**
   * Return all bytes written and reset this writer.
   */
  finish() {
    this.chunks.push(new Uint8Array(this.buf));
    let t = 0;
    for (let e = 0; e < this.chunks.length; e++)
      t += this.chunks[e].length;
    let i = new Uint8Array(t), s = 0;
    for (let e = 0; e < this.chunks.length; e++)
      i.set(this.chunks[e], s), s += this.chunks[e].length;
    return this.chunks = [], i;
  }
  /**
   * Start a new fork for length-delimited data like a message
   * or a packed repeated field.
   *
   * Must be joined later with `join()`.
   */
  fork() {
    return this.stack.push({ chunks: this.chunks, buf: this.buf }), this.chunks = [], this.buf = [], this;
  }
  /**
   * Join the last fork. Write its length and bytes, then
   * return to the previous state.
   */
  join() {
    let t = this.finish(), i = this.stack.pop();
    if (!i)
      throw new Error("invalid state, fork stack empty");
    return this.chunks = i.chunks, this.buf = i.buf, this.uint32(t.byteLength), this.raw(t);
  }
  /**
   * Writes a tag (field number and wire type).
   *
   * Equivalent to `uint32( (fieldNo << 3 | type) >>> 0 )`.
   *
   * Generated code should compute the tag ahead of time and call `uint32()`.
   */
  tag(t, i) {
    return this.uint32((t << 3 | i) >>> 0);
  }
  /**
   * Write a chunk of raw bytes.
   */
  raw(t) {
    return this.buf.length && (this.chunks.push(new Uint8Array(this.buf)), this.buf = []), this.chunks.push(t), this;
  }
  /**
   * Write a `uint32` value, an unsigned 32 bit varint.
   */
  uint32(t) {
    for (w(t); t > 127; )
      this.buf.push(t & 127 | 128), t = t >>> 7;
    return this.buf.push(t), this;
  }
  /**
   * Write a `int32` value, a signed 32 bit varint.
   */
  int32(t) {
    return f(t), l(t, this.buf), this;
  }
  /**
   * Write a `bool` value, a variant.
   */
  bool(t) {
    return this.buf.push(t ? 1 : 0), this;
  }
  /**
   * Write a `bytes` value, length-delimited arbitrary data.
   */
  bytes(t) {
    return this.uint32(t.byteLength), this.raw(t);
  }
  /**
   * Write a `string` value, length-delimited data converted to UTF-8 text.
   */
  string(t) {
    let i = this.textEncoder.encode(t);
    return this.uint32(i.byteLength), this.raw(i);
  }
  /**
   * Write a `float` value, 32-bit floating point number.
   */
  float(t) {
    p(t);
    let i = new Uint8Array(4);
    return new DataView(i.buffer).setFloat32(0, t, !0), this.raw(i);
  }
  /**
   * Write a `double` value, a 64-bit floating point number.
   */
  double(t) {
    let i = new Uint8Array(8);
    return new DataView(i.buffer).setFloat64(0, t, !0), this.raw(i);
  }
  /**
   * Write a `fixed32` value, an unsigned, fixed-length 32-bit integer.
   */
  fixed32(t) {
    w(t);
    let i = new Uint8Array(4);
    return new DataView(i.buffer).setUint32(0, t, !0), this.raw(i);
  }
  /**
   * Write a `sfixed32` value, a signed, fixed-length 32-bit integer.
   */
  sfixed32(t) {
    f(t);
    let i = new Uint8Array(4);
    return new DataView(i.buffer).setInt32(0, t, !0), this.raw(i);
  }
  /**
   * Write a `sint32` value, a signed, zigzag-encoded 32-bit varint.
   */
  sint32(t) {
    return f(t), t = (t << 1 ^ t >> 31) >>> 0, l(t, this.buf), this;
  }
  /**
   * Write a `fixed64` value, a signed, fixed-length 64-bit integer.
   */
  sfixed64(t) {
    let i = new Uint8Array(8), s = new DataView(i.buffer), e = n.enc(t);
    return s.setInt32(0, e.lo, !0), s.setInt32(4, e.hi, !0), this.raw(i);
  }
  /**
   * Write a `fixed64` value, an unsigned, fixed-length 64 bit integer.
   */
  fixed64(t) {
    let i = new Uint8Array(8), s = new DataView(i.buffer), e = n.uEnc(t);
    return s.setInt32(0, e.lo, !0), s.setInt32(4, e.hi, !0), this.raw(i);
  }
  /**
   * Write a `int64` value, a signed 64-bit varint.
   */
  int64(t) {
    let i = n.enc(t);
    return o(i.lo, i.hi, this.buf), this;
  }
  /**
   * Write a `sint64` value, a signed, zig-zag-encoded 64-bit varint.
   */
  sint64(t) {
    let i = n.enc(t), s = i.hi >> 31, e = i.lo << 1 ^ s, u = (i.hi << 1 | i.lo >>> 31) ^ s;
    return o(e, u, this.buf), this;
  }
  /**
   * Write a `uint64` value, an unsigned 64-bit varint.
   */
  uint64(t) {
    let i = n.uEnc(t);
    return o(i.lo, i.hi, this.buf), this;
  }
}
class U {
  static {
    a(this, "BinaryReader");
  }
  constructor(t, i) {
    this.varint64 = d, this.uint32 = k, this.buf = t, this.len = t.length, this.pos = 0, this.view = new DataView(t.buffer, t.byteOffset, t.byteLength), this.textDecoder = i ?? new TextDecoder();
  }
  /**
   * Reads a tag - field number and wire type.
   */
  tag() {
    let t = this.uint32(), i = t >>> 3, s = t & 7;
    if (i <= 0 || s < 0 || s > 5)
      throw new Error("illegal tag: field no " + i + " wire type " + s);
    return [i, s];
  }
  /**
   * Skip one element and return the skipped data.
   *
   * When skipping StartGroup, provide the tags field number to check for
   * matching field number in the EndGroup tag.
   */
  skip(t, i) {
    let s = this.pos;
    switch (t) {
      case h.Varint:
        for (; this.buf[this.pos++] & 128; )
          ;
        break;
      case h.Bit64:
        this.pos += 4;
      case h.Bit32:
        this.pos += 4;
        break;
      case h.LengthDelimited:
        let e = this.uint32();
        this.pos += e;
        break;
      case h.StartGroup:
        for (; ; ) {
          const [u, c] = this.tag();
          if (c === h.EndGroup) {
            if (i !== void 0 && u !== i)
              throw new Error("invalid end group tag");
            break;
          }
          this.skip(c, u);
        }
        break;
      default:
        throw new Error("cant skip wire type " + t);
    }
    return this.assertBounds(), this.buf.subarray(s, this.pos);
  }
  /**
   * Throws error if position in byte array is out of range.
   */
  assertBounds() {
    if (this.pos > this.len)
      throw new RangeError("premature EOF");
  }
  /**
   * Read a `int32` field, a signed 32 bit varint.
   */
  int32() {
    return this.uint32() | 0;
  }
  /**
   * Read a `sint32` field, a signed, zigzag-encoded 32-bit varint.
   */
  sint32() {
    let t = this.uint32();
    return t >>> 1 ^ -(t & 1);
  }
  /**
   * Read a `int64` field, a signed 64-bit varint.
   */
  int64() {
    return n.dec(...this.varint64());
  }
  /**
   * Read a `uint64` field, an unsigned 64-bit varint.
   */
  uint64() {
    return n.uDec(...this.varint64());
  }
  /**
   * Read a `sint64` field, a signed, zig-zag-encoded 64-bit varint.
   */
  sint64() {
    let [t, i] = this.varint64(), s = -(t & 1);
    return t = (t >>> 1 | (i & 1) << 31) ^ s, i = i >>> 1 ^ s, n.dec(t, i);
  }
  /**
   * Read a `bool` field, a variant.
   */
  bool() {
    let [t, i] = this.varint64();
    return t !== 0 || i !== 0;
  }
  /**
   * Read a `fixed32` field, an unsigned, fixed-length 32-bit integer.
   */
  fixed32() {
    return this.view.getUint32((this.pos += 4) - 4, !0);
  }
  /**
   * Read a `sfixed32` field, a signed, fixed-length 32-bit integer.
   */
  sfixed32() {
    return this.view.getInt32((this.pos += 4) - 4, !0);
  }
  /**
   * Read a `fixed64` field, an unsigned, fixed-length 64 bit integer.
   */
  fixed64() {
    return n.uDec(this.sfixed32(), this.sfixed32());
  }
  /**
   * Read a `fixed64` field, a signed, fixed-length 64-bit integer.
   */
  sfixed64() {
    return n.dec(this.sfixed32(), this.sfixed32());
  }
  /**
   * Read a `float` field, 32-bit floating point number.
   */
  float() {
    return this.view.getFloat32((this.pos += 4) - 4, !0);
  }
  /**
   * Read a `double` field, a 64-bit floating point number.
   */
  double() {
    return this.view.getFloat64((this.pos += 8) - 8, !0);
  }
  /**
   * Read a `bytes` field, length-delimited arbitrary data.
   */
  bytes() {
    let t = this.uint32(), i = this.pos;
    return this.pos += t, this.assertBounds(), this.buf.subarray(i, i + t);
  }
  /**
   * Read a `string` field, length-delimited data converted to UTF-8 text.
   */
  string() {
    return this.textDecoder.decode(this.bytes());
  }
}
export {
  U as BinaryReader,
  E as BinaryWriter,
  h as WireType
};
