{"version":3,"file":"lib/lib.cjs","mappings":"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","sources":["webpack://trbr/external node-commonjs \"node:child_process\"","webpack://trbr/external node-commonjs \"node:events\"","webpack://trbr/external node-commonjs \"node:fs/promises\"","webpack://trbr/external node-commonjs \"node:os\"","webpack://trbr/external node-commonjs \"node:path\"","webpack://trbr/external node-commonjs \"node:stream/promises\"","webpack://trbr/external node-commonjs \"tty\"","webpack://trbr/./src/lib/abort.js","webpack://trbr/./src/lib/capturer/framer.js","webpack://trbr/./src/lib/capturer/lineDecoder.js","webpack://trbr/./src/lib/decode/regAddr.js","webpack://trbr/./src/lib/decode/regs.js","webpack://trbr/./src/lib/decode/addr2Line.js","webpack://trbr/./src/lib/decode/gdbMi.js","webpack://trbr/./src/lib/decode/globals.js","webpack://trbr/./src/lib/decode/coredump.js","webpack://trbr/external node-commonjs \"node:net\"","webpack://trbr/./src/lib/decode/riscv.js","webpack://trbr/./src/lib/decode/xtensa.js","webpack://trbr/./src/lib/decode/decode.js","webpack://trbr/./src/lib/decode/decode.text.js","webpack://trbr/./src/lib/decode/decodeParams.js","webpack://trbr/./src/lib/decode/xtensaPanicParse.js","webpack://trbr/./src/lib/os.js","webpack://trbr/./src/lib/tool.js","webpack://trbr/./src/lib/exec.js","webpack://trbr/webpack/bootstrap","webpack://trbr/webpack/runtime/define property getters","webpack://trbr/webpack/runtime/hasOwnProperty shorthand","webpack://trbr/webpack/runtime/make namespace object","webpack://trbr/./src/lib/decode/riscvPanicParse.js","webpack://trbr/./src/lib/capturer/capturer.js","webpack://trbr/./node_modules/tinyrainbow/dist/chunk-BVHSVHOK.js","webpack://trbr/./node_modules/tinyrainbow/dist/node.js","webpack://trbr/./src/lib/decode/stringify.js"],"sourcesContent":["module.exports = require(\"node:child_process\");","module.exports = require(\"node:events\");","module.exports = require(\"node:fs/promises\");","module.exports = require(\"node:os\");","module.exports = require(\"node:path\");","module.exports = require(\"node:stream/promises\");","module.exports = require(\"tty\");","// @ts-check\n\nexport class AbortError extends Error {\n  constructor() {\n    super('User abort')\n    this.name = 'AbortError'\n    this.code = 'ABORT_ERR'\n  }\n}\n\nexport const neverSignal = new AbortController().signal\n","// @ts-check\n\n/** @typedef {import('./types.js').FramedCrashBlock} FramedCrashBlock */\n\nconst startPatterns = [\n  /Guru Meditation Error:/i,\n  /panic'ed/i,\n  /^Exception\\s+\\(\\d+\\):?/i,\n]\n\nconst reasonPatterns = [\n  /Guru Meditation Error:/i,\n  /panic'ed/i,\n  /^Exception\\s+\\(\\d+\\):?/i,\n]\n\n/**\n * @typedef {Object} FramerState\n * @property {string[]} lines\n * @property {number} startedAt\n * @property {number} lastAt\n * @property {string | undefined} reasonLine\n */\n\nexport class CrashFramer {\n  _quietPeriodMs\n  /** @type {FramerState | undefined} */\n  _active\n\n  /** @param {{ quietPeriodMs: number }} options */\n  constructor(options) {\n    this._quietPeriodMs = options.quietPeriodMs\n  }\n\n  /**\n   * @param {string} line\n   * @param {number} atMs\n   * @returns {FramedCrashBlock[]}\n   */\n  pushLine(line, atMs) {\n    /** @type {FramedCrashBlock[]} */\n    const finalized = []\n\n    this._finalizeIfQuiet(finalized, atMs)\n\n    if (isStartLine(line)) {\n      this._finalize(finalized)\n      this._active = {\n        lines: [],\n        startedAt: atMs,\n        lastAt: atMs,\n        reasonLine: undefined,\n      }\n    }\n\n    if (!this._active) {\n      return finalized\n    }\n\n    this._active.lines.push(line)\n    this._active.lastAt = atMs\n    if (!this._active.reasonLine && isReasonLine(line)) {\n      this._active.reasonLine = line.trim()\n    }\n\n    if (/^Rebooting\\.\\.\\./i.test(line.trim())) {\n      this._finalize(finalized)\n    }\n\n    return finalized\n  }\n\n  /**\n   * @param {number} atMs\n   * @returns {FramedCrashBlock[]}\n   */\n  flush(atMs) {\n    /** @type {FramedCrashBlock[]} */\n    const finalized = []\n    this._finalizeIfQuiet(finalized, atMs)\n    // Finalize on flush only when the active crash already looks complete.\n    // This avoids trailing partial events at stop-capture while still\n    // emitting complete blocks without waiting for an extra quiet period.\n    if (this._active && isCompleteBlock(this._active.lines)) {\n      this._finalize(finalized)\n    }\n    return finalized\n  }\n\n  /**\n   * @param {FramedCrashBlock[]} finalized\n   * @param {number} atMs\n   */\n  _finalizeIfQuiet(finalized, atMs) {\n    if (!this._active) {\n      return\n    }\n    if (atMs - this._active.lastAt < this._quietPeriodMs) {\n      return\n    }\n    this._finalize(finalized)\n  }\n\n  /** @param {FramedCrashBlock[]} finalized */\n  _finalize(finalized) {\n    if (!this._active) {\n      return\n    }\n    const lines = this._active.lines\n    const hasSignal = lines.some((line) => isStartLine(line))\n    if (hasSignal && lines.length > 0) {\n      finalized.push({\n        lines: [...lines],\n        startedAt: this._active.startedAt,\n        lastAt: this._active.lastAt,\n        reasonLine: this._active.reasonLine,\n      })\n    }\n    this._active = undefined\n  }\n}\n\n/**\n * @param {string} line\n * @returns {boolean}\n */\nfunction isStartLine(line) {\n  return startPatterns.some((pattern) => pattern.test(line))\n}\n\n/**\n * @param {string} line\n * @returns {boolean}\n */\nfunction isReasonLine(line) {\n  return reasonPatterns.some((pattern) => pattern.test(line))\n}\n\n/**\n * @param {string[]} lines\n * @returns {boolean}\n */\nfunction isCompleteBlock(lines) {\n  return lines.some((line) =>\n    [\n      /Backtrace:/i,\n      /^Stack memory:/i,\n      /^Rebooting\\.\\.\\./i,\n      /ELF file SHA256:/i,\n    ].some((pattern) => pattern.test(line.trim()))\n  )\n}\n","// @ts-check\n\nexport class LineDecoder {\n  _decoder = new TextDecoder('utf-8')\n  _buffer = ''\n\n  /**\n   * @param {Uint8Array} chunk\n   * @returns {string[]}\n   */\n  push(chunk) {\n    this._buffer += this._decoder.decode(chunk, { stream: true })\n    return this._drain(false)\n  }\n\n  /** @returns {string[]} */\n  flush() {\n    this._buffer += this._decoder.decode()\n    return this._drain(true)\n  }\n\n  /**\n   * @param {boolean} isFinal\n   * @returns {string[]}\n   */\n  _drain(isFinal) {\n    /** @type {string[]} */\n    const lines = []\n    let start = 0\n\n    for (let i = 0; i < this._buffer.length; i++) {\n      const ch = this._buffer.charCodeAt(i)\n      if (ch !== 10 && ch !== 13) {\n        continue\n      }\n      if (ch === 13 && i === this._buffer.length - 1 && !isFinal) {\n        break\n      }\n\n      lines.push(this._buffer.slice(start, i))\n      if (ch === 13 && this._buffer.charCodeAt(i + 1) === 10) {\n        i++\n      }\n      start = i + 1\n    }\n\n    if (isFinal) {\n      if (start < this._buffer.length) {\n        lines.push(this._buffer.slice(start))\n      }\n      this._buffer = ''\n      return lines\n    }\n\n    this._buffer = this._buffer.slice(start)\n    return lines\n  }\n}\n","// @ts-check\n\nimport { isGDBLine, isParsedGDBLine } from './decode.js'\n\n/** @typedef {import('./decode.js').Debug} Debug */\n\nconst envDebugEnabled = process.env.TRBR_DEBUG === 'true'\nconst regAddrLogPrefix = '[trbr][reg-addr]'\n\n/**\n * @param {Debug} [debug]\n * @returns {Debug}\n */\nfunction createRegAddrLogger(debug) {\n  const writer = debug ?? (envDebugEnabled ? console.log : undefined)\n  return writer ? (...args) => writer(regAddrLogPrefix, ...args) : () => {}\n}\n\n/**\n * @param {GDBLine | ParsedGDBLine | undefined} entry\n * @returns {entry is GDBLine | ParsedGDBLine}\n */\nfunction isParsedOrGdbLine(entry) {\n  return Boolean(entry) && (isGDBLine(entry) || isParsedGDBLine(entry))\n}\n\n/**\n * Parses a method signature string into its name and argument list.\n *\n * @param {string} sig\n * @returns {{\n *   name: string\n *   args: { name: string; value?: string; type?: string }[]\n * }}\n */\nfunction parseMethodSignature(sig) {\n  const nameMatch = sig.match(/^([^(]+)\\s*\\((.*)\\)$/s)\n  if (!nameMatch) {\n    return { name: sig.trim(), args: [] }\n  }\n\n  const [, name, argsStr] = nameMatch\n  const args =\n    argsStr.match(/(?:[^,\"']+|\"[^\"]*\"|'[^']*')+/g)?.map((arg) => {\n      const parts = arg.split('=')\n      if (parts.length === 2) {\n        const [name, value] = parts.map((s) => s.trim())\n        return { name, value }\n      } else {\n        return { name: arg.trim() }\n      }\n    }) || []\n  return { name: name.trim(), args }\n}\n\n/** @typedef {string} RegAddr `'0x12345678'` or `'this::loop'` */\n\n/**\n * @typedef {Object} GDBLine\n * @property {RegAddr} regAddr\n * @property {string} lineNumber `'36'` or `'??'`\n */\n\n/**\n * @typedef {GDBLine & {\n *   file: string\n *   method: string\n * }} ParsedGDBLine\n */\n\n/**\n * @param {string} stdout\n * @param {Debug} [debug]\n * @returns {(GDBLine | ParsedGDBLine)[]}\n */\nexport function parseLines(stdout, debug) {\n  const log = createRegAddrLogger(debug)\n  return stdout\n    .split(/\\r?\\n/)\n    .map((line) => line.trim())\n    .filter(Boolean)\n    .map((line) => parseLine(line, log))\n    .filter(isParsedOrGdbLine)\n}\n\n/**\n * @param {string} line\n * @param {Debug} [log]\n * @returns {GDBLine | ParsedGDBLine | undefined}\n */\nexport function parseLine(line, log = createRegAddrLogger()) {\n  log('parse line', line)\n  const patterns = [\n    // GDB style with frame number and numeric file/line\n    /#\\d+\\s+(0x[0-9a-f]+)\\s+in\\s+([^(]+\\((?:\"(?:\\\\.|[^\"\\\\])*\"|[^()])*?\\))\\s+at\\s+(.+):(\\d+)/i,\n    // GDB style without frame number and numeric file/line\n    /(0x[0-9a-f]+)\\s+in\\s+([^(]+(?:\\([^()]*\\))?)\\s+at\\s+(.+):(\\d+)/i,\n    // GDB style with frame number and ?? file/line\n    /(?:#\\d+\\s+)?(0x[0-9a-f]+)\\s+in\\s+([^(]+(?:\\([^()]*\\))?)\\s+at\\s+(\\?+):(\\?+)/i,\n    // \"is in\" format with numeric file/line\n    /(0x[0-9a-f]+)\\s+is\\s+in\\s+([^(]+(?:\\([^()]*\\))?)\\s+\\((.+):(\\d+)\\)/i,\n    // \"is in\" format without line number\n    /(0x[0-9a-f]+)\\s+is\\s+in\\s+([^(]+(?:\\([^()]*\\))?)\\s+\\(([^():]+)\\)/i,\n    // Address with \"is at\" and numeric file/line\n    /(0x[0-9a-f]+)\\s+is\\s+at\\s+(.+):(\\d+)/i,\n    // Method with file/line but no address\n    /(?:#\\d+\\s+)?([^(]+(?:\\([^()]*\\))?)\\s+at\\s+(.+):(\\d+)/,\n  ]\n\n  for (const [i, pattern] of patterns.entries()) {\n    const match = line.match(pattern)\n    if (match) {\n      // Numeric file/line after \"in\"\n      if (i === 0 || i === 1) {\n        const [, regAddr, method, file, lineNumber] = match\n        return normalizeParsedLine({ regAddr, method, file, lineNumber })\n      }\n      // ?? file/line after \"in\"\n      if (i === 2) {\n        const [, regAddr, method, file, lineNumber] = match\n        return normalizeParsedLine({ regAddr, method, file, lineNumber })\n      }\n      // \"is in\" with numeric file/line\n      if (i === 3) {\n        const [, regAddr, method, file, lineNumber] = match\n        return normalizeParsedLine({ regAddr, method, file, lineNumber })\n      }\n      // \"is in\" without line number\n      if (i === 4) {\n        const [, regAddr, method, file] = match\n        return normalizeParsedLine({ regAddr, method, file, lineNumber: '??' })\n      }\n      // \"is at\" with numeric file/line\n      if (i === 5) {\n        const [, regAddr, file, lineNumber] = match\n        return normalizeParsedLine({ regAddr, method: '??', file, lineNumber })\n      }\n      // Method with file/line but no address\n      if (i === 6) {\n        const [, method, file, lineNumber] = match\n        return normalizeParsedLine({ regAddr: '??', method, file, lineNumber })\n      }\n    }\n  }\n  // Fallback for addresses without file/line info\n  const fallbackMatch = line.match(\n    /(?:#\\d+\\s+)?(0x[0-9a-f]+)\\s+(?:is\\s+in|in)\\s+([^(]+(?:\\([^()]*\\))?)/i\n  )\n  if (fallbackMatch) {\n    const [, regAddr, method] = fallbackMatch\n    return normalizeParsedLine({\n      regAddr,\n      method: method.trim(),\n      file: '??',\n      lineNumber: '??',\n    })\n  }\n  log('no pattern matched', line)\n  return undefined\n}\n\n/**\n * Normalize a parsed GDB line entry. If both file and lineNumber are missing or\n * unknown, omit them. If either is present but unknown, default to '??'.\n *\n * @param {ParsedGDBLine} entry\n * @returns {GDBLine | ParsedGDBLine}\n */\n/**\n * Normalize a parsed GDB line entry. If both file and lineNumber are missing or\n * unknown, omit them. If either is present but unknown, default to '??'.\n *\n * @param {ParsedGDBLine} entry\n * @returns {GDBLine | ParsedGDBLine}\n */\nfunction normalizeParsedLine(entry) {\n  const { file, lineNumber, method, regAddr } = entry\n  const parsedMethod = parseMethodSignature(method)\n\n  const hasValidFile = file && file !== '' && file !== '??'\n  const hasValidLine = lineNumber && lineNumber !== '' && lineNumber !== '??'\n\n  if (hasValidFile || hasValidLine) {\n    const result = {\n      regAddr,\n      method: parsedMethod.name,\n      file: hasValidFile ? file : '??',\n      lineNumber: hasValidLine ? lineNumber : '??',\n    }\n    if (parsedMethod.args && parsedMethod.args.length > 0) {\n      Object.assign(result, { args: parsedMethod.args })\n    }\n    return result\n  }\n\n  const hasValidMethod =\n    parsedMethod.name &&\n    parsedMethod.name !== '' &&\n    parsedMethod.name !== '??' &&\n    parsedMethod.name !== '?? ()'\n\n  if (!hasValidLine && hasValidMethod) {\n    return { regAddr, lineNumber: parsedMethod.name }\n  }\n\n  return { regAddr, lineNumber: lineNumber || '??' }\n}\n","// @ts-check\n\nexport const registerSets = /** @type {const} */ ({\n  // Xtensa exception frame order used in ESP‑IDF v5 core dumps\n  xtensa: [\n    'PC',\n    'PS',\n    // loop registers + SAR\n    'LBEG',\n    'LEND',\n    'LCOUNT',\n    'SAR',\n    // general‑purpose registers\n    'A0',\n    'A1',\n    'A2',\n    'A3',\n    'A4',\n    'A5',\n    'A6',\n    'A7',\n    'A8',\n    'A9',\n    'A10',\n    'A11',\n    'A12',\n    'A13',\n    'A14',\n    'A15',\n    // remaining exception/window registers\n    'EXCCAUSE',\n    'EXCVADDR',\n    'WINDOWBASE',\n    'WINDOWSTART',\n  ],\n  // TODO: compare with gdbRegsInfoRiscvIlp32\n  riscv: [\n    'MEPC',\n    'RA',\n    'SP',\n    'GP',\n    'TP',\n    'T0',\n    'T1',\n    'T2',\n    'S0',\n    'S1',\n    'A0',\n    'A1',\n    'A2',\n    'A3',\n    'A4',\n    'A5',\n    'A6',\n    'A7',\n    'S2',\n    'S3',\n    'S4',\n    'S5',\n    'S6',\n    'S7',\n    'S8',\n    'S9',\n    'S10',\n    'S11',\n    'T3',\n    'T4',\n    'T5',\n    'T6',\n    'MSTATUS',\n    'MTVEC',\n    'MCAUSE',\n    'MTVAL',\n    'MHARTID',\n  ],\n})\n\n/**\n * @param {number} number\n * @returns {string}\n */\nexport function toHexString(number = 0) {\n  return `0x${number.toString(16).padStart(8, '0')}`\n}\n","// @ts-check\n\nimport { spawn } from 'node:child_process'\n\nimport { isParsedGDBLine } from './decode.js'\nimport { parseLines } from './regAddr.js'\nimport { toHexString } from './regs.js'\n\n/**\n * @typedef {Object} CommandQueueItem\n * @property {string} cmd\n * @property {(result: string) => void} resolve\n * @property {(reason: unknown) => void} reject\n */\n\nconst prompt = '(gdb)'\nconst notExecutableFormat = 'not in executable format'\nconst fileFormatNotRecognized = 'file format not recognized'\nconst noSuchFileOrDirectory = 'No such file or directory'\n\nclass GDBSession {\n  /**\n   * @param {Pick<DecodeParams, 'elfPath' | 'toolPath'>} params\n   * @param {DecodeOptions} [options={}] Default is `{}`\n   */\n  constructor({ toolPath, elfPath }, options = {}) {\n    this.toolPath = toolPath\n    this.elfPath = elfPath\n    this.error = null\n    this.didExecuteFirstCommand = false\n    this.gdb = spawn(toolPath, [elfPath], {\n      stdio: 'pipe',\n      signal: options.signal,\n    })\n    this.buffer = ''\n    /** @type {CommandQueueItem[]} */\n    this.queue = []\n    this.current = null\n    this.gdb.stdout.on('data', (chunk) => this._onData(chunk))\n    this.gdb.stderr.on('data', (chunk) => this._onData(chunk))\n    this.gdb.on('error', (err) => this.current?.reject(err))\n    this.gdb.on('exit', (code, signal) => {\n      if (code !== 0 && signal !== 'SIGTERM') {\n        console.warn(`GDB exited with code ${code} or signal ${signal}`)\n      }\n    })\n  }\n\n  /** @param {Buffer} chunk */\n  _onData(chunk) {\n    this.buffer += chunk.toString()\n    if (!this.current) {\n      return\n    }\n    const idx = this.buffer.indexOf(prompt)\n    if (idx === -1) {\n      return\n    }\n    const output = this.buffer.slice(0, idx)\n    this.buffer = this.buffer.slice(idx + prompt.length)\n    const { resolve } = this.current\n    this.current = null\n    resolve(output)\n    this._processQueue()\n  }\n\n  _processQueue() {\n    const item = this.queue.shift()\n    if (this.current || !item) {\n      return\n    }\n    const { cmd, resolve, reject } = item\n    this.current = { resolve, reject }\n    this.gdb.stdin.write(cmd + '\\n')\n  }\n\n  start() {\n    return new Promise((resolve, reject) => {\n      // GDB not found\n      const onError = (/** @type {Error} */ error) => {\n        let userError = error\n        if (\n          error instanceof Error &&\n          'code' in error &&\n          error.code === 'ENOENT'\n        ) {\n          userError = new Error(`GDB tool not found at ${this.toolPath}`)\n        }\n        reject(userError)\n      }\n\n      const onData = (/** @type {Buffer} */ chunk) => {\n        // ELF is not found\n        if (\n          !this.didExecuteFirstCommand &&\n          this.buffer.includes(noSuchFileOrDirectory)\n        ) {\n          if (!this.error) {\n            this.error = new Error(\n              `The ELF file does not exist or is not readable: ${this.elfPath}`\n            )\n            reject(this.error)\n          }\n          return\n        }\n\n        // Not an ELF\n        if (\n          !this.didExecuteFirstCommand &&\n          (this.buffer.includes(notExecutableFormat) ||\n            this.buffer.includes(fileFormatNotRecognized))\n        ) {\n          if (!this.error) {\n            this.error = new Error(\n              `The ELF file is not in executable format: ${this.elfPath}`\n            )\n            reject(this.error)\n          }\n          return\n        }\n\n        this.buffer += chunk.toString()\n        const idx = this.buffer.indexOf(prompt)\n        if (idx !== -1) {\n          this.buffer = this.buffer.slice(idx + prompt.length)\n          resolve('')\n        }\n      }\n      this.gdb.on('error', onError)\n      this.gdb.stdout.on('data', onData)\n      this.gdb.stderr.on('data', onData)\n    })\n  }\n\n  /** @param {string} cmd */\n  async exec(cmd) {\n    if (this.error) {\n      this.close()\n      return Promise.reject(this.error)\n    }\n    const result = await new Promise((resolve, reject) => {\n      this.queue.push({ cmd, resolve, reject })\n      this._processQueue()\n    })\n\n    this.didExecuteFirstCommand = true\n    return result\n  }\n\n  async close() {\n    if (!this.gdb.killed) {\n      this.gdb.stdin.end()\n      this.gdb.kill('SIGTERM')\n      if (typeof this.gdb.exitCode !== 'number') {\n        await new Promise((resolve) => this.gdb.once('exit', resolve))\n      }\n    }\n  }\n}\n\n/** @typedef {import('./decode.js').DecodeParams} DecodeParams */\n/** @typedef {import('./decode.js').DecodeOptions} DecodeOptions */\n/** @typedef {import('./decode.js').GDBLine} GDBLine */\n/** @typedef {import('./decode.js').ParsedGDBLine} ParsedGDBLine */\n/** @typedef {import('./decode.js').AddrLine} AddrLine */\n\n/**\n * @param {(number | AddrLine | undefined)[]} addrs\n * @returns {number[]}\n */\nfunction buildAddr2LineAddrs(addrs) {\n  /** @type {Set<number>} */\n  const dedupedAddrs = new Set()\n  for (const addr of addrs) {\n    let addrNumber\n    if (typeof addr === 'object') {\n      addrNumber = addr.addr\n    } else if (typeof addr === 'number') {\n      addrNumber = addr\n    }\n    if (addrNumber !== undefined && !dedupedAddrs.has(addrNumber)) {\n      dedupedAddrs.add(addrNumber)\n    }\n  }\n  return Array.from(dedupedAddrs.values())\n}\n\n/**\n * @typedef {Object} RegsInfo\n * @property {Record<number, Record<string, number>>} threadRegs\n * @property {number} [currentThreadAddr]\n */\n\n/**\n * @param {Pick<DecodeParams, 'elfPath' | 'toolPath'>} params\n * @param {(number | AddrLine | undefined)[]} addrs\n * @param {DecodeOptions} [options={}] Default is `{}`\n * @returns {Promise<AddrLine[]>}\n */\nexport async function addr2line({ elfPath, toolPath }, addrs, options = {}) {\n  const addresses = buildAddr2LineAddrs(addrs)\n  if (!addresses.length) {\n    throw new Error('No register addresses found to decode')\n  }\n\n  const results = new Map()\n  const session = new GDBSession({ elfPath, toolPath }, options)\n\n  try {\n    await session.start()\n    await session.exec('set pagination off')\n    await session.exec('set listsize 1')\n    for (const addr of addresses) {\n      const hex = toHexString(addr)\n      const listOutput = await session.exec(`list *${hex}`)\n      let parsedLines = parseLines(listOutput, options.debug)\n      let location = parsedLines.find(isParsedGDBLine)\n      if (!location) {\n        const lineOutput = await session.exec(`info line *${hex}`)\n        parsedLines = parseLines(lineOutput, options.debug)\n        location = parsedLines.find(isParsedGDBLine)\n      }\n      results.set(addr, {\n        addr,\n        location: location ?? { regAddr: hex, lineNumber: '??' },\n      })\n    }\n  } finally {\n    await session.close()\n  }\n\n  return addrs.map((addrOrLine) => {\n    const addr = typeof addrOrLine === 'object' ? addrOrLine.addr : addrOrLine\n    return results.get(addr) || { location: '??' }\n  })\n}\n","// @ts-check\n\nimport cp from 'node:child_process'\n\nimport { AbortError } from '../abort.js'\n\nlet clientSeq = 0\n\n/**\n * @param {number} id\n * @param {import('./decode.js').Debug | undefined} debug\n * @returns {(...args: unknown[]) => void}\n */\nfunction createLogger(id, debug) {\n  const prefix = `[trbr][gdb-mi:${id}]`\n  const writer =\n    debug ?? (process.env.TRBR_DEBUG === 'true' ? console.log : undefined)\n  return writer ? (...args) => writer(prefix, ...args) : () => {}\n}\n\n/**\n * @param {string} text\n * @param {number} [limit=400] Default is `400`\n * @returns {string}\n */\nfunction preview(text, limit = 400) {\n  if (text.length <= limit) {\n    return text\n  }\n  return `${text.slice(0, limit)}...[truncated ${text.length - limit} chars]`\n}\n\n/** Minimal GDB MI client for queueing commands and reading result records. */\nexport class GdbMiClient {\n  /**\n   * @param {string} gdbPath\n   * @param {string[]} args\n   * @param {import('./decode.js').DecodeOptions} [options={}] Default is `{}`\n   */\n  constructor(gdbPath, args, options = {}) {\n    this.cp = cp.spawn(gdbPath, args, { stdio: 'pipe', signal: options.signal })\n    this.id = ++clientSeq\n    this.log = createLogger(this.id, options.debug)\n    this.log('spawn', gdbPath, args.join(' '))\n    /** @type {Error | undefined} */\n    this.error = undefined\n    /**\n     * @type {{\n     *   resolve: (value: string) => void\n     *   reject: (err: Error) => void\n     *   command: string\n     *   startedAt: number\n     * }[]}\n     */\n    this.commandQueue = []\n\n    this.signal = options.signal\n    if (this.signal) {\n      this.signal.addEventListener('abort', () => {\n        const abortErr = new AbortError()\n        this.error = abortErr\n        this.log('abort signal received')\n        this.commandQueue.forEach((executor) => executor.reject(abortErr))\n        this.commandQueue = []\n      })\n    }\n\n    this.stdoutBuffer = ''\n    this.cp.stdout.on('data', (chunk) => this._onData(chunk))\n    this.cp.stderr.on('data', (chunk) => this._onData(chunk))\n    this.cp.on('error', (err) => {\n      this.error = err\n      this.log('process error', err)\n      this.commandQueue.forEach((executor) => executor.reject(err))\n      this.commandQueue = []\n    })\n    this.cp.on('exit', (code, signal) => {\n      this.log('process exit', { code, signal })\n    })\n  }\n\n  /**\n   * @param {string} command\n   * @returns {Promise<string>}\n   */\n  sendCommand(command) {\n    if (this.error) {\n      return Promise.reject(this.error)\n    }\n    this.log('send', command)\n    return new Promise((resolve, reject) => {\n      const executor = { resolve, reject, command, startedAt: Date.now() }\n      this.commandQueue.push(executor)\n      this.cp.stdin.write(`${command}\\n`)\n    })\n  }\n\n  /** @param {Buffer} chunk */\n  _onData(chunk) {\n    if (this.error) {\n      const error = this.error\n      this.commandQueue.forEach((executor) => executor.reject(error))\n      this.commandQueue = []\n    }\n\n    this.stdoutBuffer += chunk.toString()\n    if (/\\(gdb\\)\\s*$/m.test(this.stdoutBuffer)) {\n      const output = this.stdoutBuffer\n      this.stdoutBuffer = ''\n      const executor = this.commandQueue.shift()\n      if (executor) {\n        const elapsed = Date.now() - executor.startedAt\n        this.log('recv', `${executor.command} (${elapsed}ms)`, preview(output))\n      } else {\n        this.log('recv without queued command', preview(output))\n      }\n      executor?.resolve(output)\n    }\n  }\n\n  close() {\n    this.log('close')\n    this.cp.stdin.end()\n    this.cp.kill()\n  }\n\n  /** @returns {Promise<void>} */\n  async drainHandshake() {\n    this.log('handshake start')\n    return new Promise((resolve, reject) => {\n      const startedAt = Date.now()\n      const onData = (/** @type {Buffer} */ chunk) => {\n        if (this.error) {\n          this.cp.stdout.off('data', onData)\n          this.log('handshake error', this.error)\n          reject(this.error)\n          return\n        }\n        this.stdoutBuffer += chunk.toString()\n        if (/\\(gdb\\)\\s*$/m.test(this.stdoutBuffer)) {\n          this.cp.stdout.off('data', onData)\n          if (this.signal) {\n            this.signal.removeEventListener('abort', onAbort)\n          }\n          this.stdoutBuffer = ''\n          this.log('handshake done', `${Date.now() - startedAt}ms`)\n          resolve()\n        }\n      }\n      const onAbort = () => {\n        this.cp.stdout.off('data', onData)\n        this.signal?.removeEventListener('abort', onAbort)\n        this.log('handshake aborted')\n        reject(new AbortError())\n      }\n      this.cp.stdout.on('data', onData)\n      this.signal?.addEventListener('abort', onAbort)\n    })\n  }\n}\n\n/**\n * @param {string} str\n * @param {string} key\n * @returns {string | undefined}\n */\nexport function extractMiListContent(str, key) {\n  const keyPattern = `${key}=[`\n  const idx = str.indexOf(keyPattern)\n  if (idx < 0) {\n    return undefined\n  }\n  const start = str.indexOf('[', idx)\n  if (start < 0) {\n    return undefined\n  }\n  let depth = 0\n  for (let i = start; i < str.length; i++) {\n    const c = str[i]\n    if (c === '[') {\n      depth++\n    } else if (c === ']') {\n      depth--\n      if (depth === 0) {\n        return str.substring(start + 1, i)\n      }\n    }\n  }\n  return undefined\n}\n\n/**\n * @param {string} listContent\n * @returns {string[]}\n */\nfunction splitMiListItems(listContent) {\n  const items = []\n  let current = ''\n  let depth = 0\n  let inQuotes = false\n  let escape = false\n\n  for (const char of listContent) {\n    if (escape) {\n      current += char\n      escape = false\n      continue\n    }\n\n    if (inQuotes && char === '\\\\') {\n      current += char\n      escape = true\n      continue\n    }\n\n    if (char === '\"') {\n      inQuotes = !inQuotes\n      current += char\n      continue\n    }\n\n    if (!inQuotes) {\n      if (char === '{' || char === '[') {\n        depth++\n      } else if (char === '}' || char === ']') {\n        depth = Math.max(0, depth - 1)\n      } else if (char === ',' && depth === 0) {\n        if (current.trim()) {\n          items.push(current.trim())\n        }\n        current = ''\n        continue\n      }\n    }\n\n    current += char\n  }\n\n  if (current.trim()) {\n    items.push(current.trim())\n  }\n\n  return items\n}\n\n/**\n * @param {string} value\n * @returns {string}\n */\nfunction unescapeMiString(value) {\n  let result = ''\n\n  for (let i = 0; i < value.length; i++) {\n    const char = value[i]\n    if (char !== '\\\\') {\n      result += char\n      continue\n    }\n\n    const next = value[i + 1]\n    if (!next) {\n      result += '\\\\'\n      continue\n    }\n    i++\n\n    switch (next) {\n      case '\\\\':\n        result += '\\\\'\n        break\n      case '\"':\n        result += '\"'\n        break\n      case 'n':\n        result += '\\n'\n        break\n      case 'r':\n        result += '\\r'\n        break\n      case 't':\n        result += '\\t'\n        break\n      default:\n        result += next\n        break\n    }\n  }\n\n  return result\n}\n\n/**\n * @param {string} tupleContent\n * @returns {Record<string, string>}\n */\nfunction parseMiTuple(tupleContent) {\n  /** @type {Record<string, string>} */\n  const result = {}\n  for (const field of splitMiListItems(tupleContent)) {\n    const idx = field.indexOf('=')\n    if (idx === -1) {\n      continue\n    }\n    const key = field.slice(0, idx).trim()\n    const rawValue = field.slice(idx + 1).trim()\n    const value =\n      rawValue.startsWith('\"') && rawValue.endsWith('\"')\n        ? unescapeMiString(rawValue.slice(1, -1))\n        : rawValue\n    result[key] = value\n  }\n  return result\n}\n\n/**\n * @param {string} raw\n * @returns {Record<string, string>}\n */\nexport function parseMiResultRecord(raw) {\n  const match = raw.match(/(?:^|\\n)\\d*\\^done(?:,([^\\r\\n]*))?/)\n  if (!match) {\n    return {}\n  }\n  const content = (match[1] ?? '').trim()\n  if (!content) {\n    return {}\n  }\n  return parseMiTuple(content)\n}\n\n/**\n * @param {string | undefined} value\n * @returns {string | undefined}\n */\nexport function stripMiList(value) {\n  if (!value) {\n    return undefined\n  }\n  const trimmed = value.trim()\n  if (trimmed.startsWith('[') && trimmed.endsWith(']')) {\n    return trimmed.slice(1, -1)\n  }\n  return undefined\n}\n\n/**\n * @param {string | undefined} listContent\n * @param {string} [tupleKey]\n * @returns {Record<string, string>[]}\n */\nexport function parseMiTupleList(listContent, tupleKey) {\n  if (!listContent) {\n    return []\n  }\n  const items = splitMiListItems(listContent)\n  /** @type {Record<string, string>[]} */\n  const tuples = []\n\n  for (const item of items) {\n    const trimmed = item.trim()\n    let tupleBody\n    if (tupleKey) {\n      const prefix = `${tupleKey}={`\n      if (!trimmed.startsWith(prefix) || !trimmed.endsWith('}')) {\n        continue\n      }\n      tupleBody = trimmed.slice(prefix.length, -1)\n    } else {\n      if (!trimmed.startsWith('{') || !trimmed.endsWith('}')) {\n        continue\n      }\n      tupleBody = trimmed.slice(1, -1)\n    }\n    tuples.push(parseMiTuple(tupleBody))\n  }\n\n  return tuples\n}\n","// @ts-check\n\nimport { GdbMiClient, extractMiListContent, parseMiTupleList } from './gdbMi.js'\n\n/** @typedef {import('./decode.js').DecodeParams} DecodeParams */\n/** @typedef {import('./decode.js').DecodeOptions} DecodeOptions */\n/** @typedef {import('./decode.js').FrameVar} FrameVar */\n/** @typedef {import('./decode.js').Debug} Debug */\n\nconst envDebugEnabled = process.env.TRBR_DEBUG === 'true'\nconst allowInfoFallback =\n  process.env.TRBR_GLOBALS_ALLOW_INFO_VARIABLES === 'true'\nconst miErrorPattern = /^\\^error/m\nconst miUnsupportedPattern = /code=\"undefined-command\"/\nconst globalsLogPrefix = '[trbr][globals]'\nconst defaultGlobalsTimeoutMs = 20_000\nconst xtensaLx106ToolHint = 'xtensa-lx106-elf-gdb'\n\n/**\n * @param {Debug | undefined} debug\n * @returns {Debug}\n */\nfunction createGlobalsLogger(debug) {\n  const writer = debug ?? (envDebugEnabled ? console.log : undefined)\n  return writer ? (...args) => writer(globalsLogPrefix, ...args) : () => {}\n}\n\n/** @returns {number} */\nfunction getGlobalsTimeoutMs() {\n  const raw = process.env.TRBR_GLOBALS_TIMEOUT_MS\n  if (!raw) {\n    return defaultGlobalsTimeoutMs\n  }\n  const parsed = Number.parseInt(raw, 10)\n  return Number.isFinite(parsed) && parsed > 0\n    ? parsed\n    : defaultGlobalsTimeoutMs\n}\n\n/**\n * @param {Pick<DecodeParams, 'toolPath' | 'elfPath'> & {\n *   coredumpMode?: boolean\n * }} params\n * @returns {boolean}\n */\nfunction shouldAllowInfoFallback(params) {\n  if (allowInfoFallback) {\n    return true\n  }\n  return Boolean(params.coredumpMode)\n}\n\n/**\n * @param {string} value\n * @returns {string}\n */\nfunction unescapeMiString(value) {\n  return value\n    .replace(/\\\\\\\\/g, '\\\\')\n    .replace(/\\\\\"/g, '\"')\n    .replace(/\\\\n/g, '\\n')\n    .replace(/\\\\r/g, '\\r')\n    .replace(/\\\\t/g, '\\t')\n}\n\n/**\n * @param {string} raw\n * @returns {string}\n */\nfunction extractMiConsoleText(raw) {\n  let text = ''\n  for (const line of raw.split(/\\r?\\n/)) {\n    const match = line.match(/^~\"(.*)\"$/)\n    if (!match) {\n      continue\n    }\n    text += unescapeMiString(match[1])\n  }\n  return text\n}\n\n/**\n * @param {string} line\n * @returns {{ name: string; type?: string; address?: string } | undefined}\n */\nfunction parseVariableLine(line) {\n  const trimmed = line.trim()\n  if (!trimmed) {\n    return undefined\n  }\n\n  const addrMatch = trimmed.match(/^(0x[0-9a-fA-F]+)\\s+(.+)$/)\n  if (addrMatch) {\n    return { address: addrMatch[1], name: addrMatch[2].trim() }\n  }\n\n  const sanitized = trimmed.endsWith(';')\n    ? trimmed.slice(0, -1).trim()\n    : trimmed\n  const lastSpace = sanitized.lastIndexOf(' ')\n  if (lastSpace === -1) {\n    return undefined\n  }\n\n  let rawName = sanitized.slice(lastSpace + 1).trim()\n  let type = sanitized.slice(0, lastSpace).trim()\n  if (!rawName) {\n    return undefined\n  }\n\n  const pointerPrefix = rawName.match(/^[*&]+/)\n  if (pointerPrefix) {\n    rawName = rawName.slice(pointerPrefix[0].length)\n    type = `${type} ${pointerPrefix[0]}`.trim()\n  }\n\n  const arrayMatch = rawName.match(/^(.*)(\\[[^\\]]+\\])$/)\n  if (arrayMatch) {\n    rawName = arrayMatch[1]\n    type = `${type} ${arrayMatch[2]}`.trim()\n  }\n\n  if (!rawName) {\n    return undefined\n  }\n\n  return { name: rawName, type }\n}\n\n/**\n * @param {string} consoleText\n * @returns {FrameVar[]}\n */\nfunction parseInfoVariables(consoleText) {\n  /** @type {FrameVar[]} */\n  const vars = []\n  for (const line of consoleText.split(/\\r?\\n/)) {\n    const trimmed = line.trim()\n    if (\n      !trimmed ||\n      trimmed.endsWith(':') ||\n      trimmed.startsWith('All defined variables') ||\n      trimmed.startsWith('File ') ||\n      trimmed.startsWith('Non-debugging symbols')\n    ) {\n      continue\n    }\n\n    const parsed = parseVariableLine(trimmed)\n    if (!parsed?.name) {\n      continue\n    }\n\n    vars.push({\n      scope: 'global',\n      name: parsed.name,\n      type: parsed.type,\n      address: parsed.address,\n    })\n  }\n  return vars\n}\n\n/**\n * @param {Record<string, string>} tuple\n * @returns {FrameVar | undefined}\n */\nfunction toGlobalVar(tuple) {\n  if (!tuple.name) {\n    return undefined\n  }\n  /** @type {FrameVar} */\n  const variable = { scope: 'global', name: tuple.name }\n  if (tuple.type) {\n    variable.type = tuple.type\n  }\n  if (tuple.addr || tuple.address) {\n    variable.address = tuple.addr || tuple.address\n  }\n  return variable\n}\n\n/**\n * @param {GdbMiClient} client\n * @param {string} flag\n * @returns {Promise<FrameVar[] | null | undefined>}\n */\nasync function tryMiSymbolList(client, flag) {\n  const raw = await client.sendCommand(`-symbol-list-variables ${flag}`)\n  if (miErrorPattern.test(raw)) {\n    if (miUnsupportedPattern.test(raw)) {\n      return null\n    }\n    return undefined\n  }\n\n  const listContent = extractMiListContent(raw, 'variables')\n  if (listContent === undefined) {\n    return []\n  }\n\n  return /** @type {FrameVar[]} */ (\n    parseMiTupleList(listContent)\n      .map(toGlobalVar)\n      .filter((value) => Boolean(value))\n  )\n}\n\n/**\n * @param {FrameVar[]} vars\n * @returns {FrameVar[]}\n */\nfunction dedupeGlobals(vars) {\n  /** @type {Map<string, FrameVar>} */\n  const map = new Map()\n  for (const variable of vars) {\n    if (!variable.name) {\n      continue\n    }\n    const existing = map.get(variable.name)\n    if (!existing) {\n      map.set(variable.name, variable)\n      continue\n    }\n    if (!existing.address && variable.address) {\n      map.set(variable.name, { ...existing, ...variable })\n      continue\n    }\n    if (!existing.type && variable.type) {\n      map.set(variable.name, { ...existing, ...variable })\n    }\n  }\n  return Array.from(map.values())\n}\n\n/**\n * @param {Pick<DecodeParams, 'toolPath' | 'elfPath'> & {\n *   coredumpMode?: boolean\n * }} params\n * @param {DecodeOptions} [options={}] Default is `{}`\n * @returns {Promise<FrameVar[]>}\n */\nexport async function listGlobalSymbols(params, options = {}) {\n  const { toolPath, elfPath } = params\n  const allowInfo = shouldAllowInfoFallback(params)\n  const log = createGlobalsLogger(options.debug)\n  log('start', { toolPath, elfPath })\n  const client = new GdbMiClient(\n    toolPath,\n    ['--interpreter=mi2', '-n', elfPath],\n    options\n  )\n\n  try {\n    await client.drainHandshake()\n\n    const globalVars = await tryMiSymbolList(client, '--global')\n    const staticVars = await tryMiSymbolList(client, '--static')\n    log('mi globals', globalVars ? globalVars.length : undefined)\n    log('mi statics', staticVars ? staticVars.length : undefined)\n    const miUnsupported = globalVars === null || staticVars === null\n\n    let combined = [...(globalVars ?? []), ...(staticVars ?? [])]\n\n    if (!combined.length && miUnsupported && !allowInfo) {\n      log('skip info variables fallback', { reason: 'mi-unsupported' })\n      return []\n    }\n\n    if (!combined.length) {\n      log('fallback to info variables')\n      const infoRaw = await client.sendCommand(\n        '-interpreter-exec console \"info variables\"'\n      )\n      combined = parseInfoVariables(extractMiConsoleText(infoRaw))\n      log('info variables count', combined.length)\n    }\n\n    const deduped = dedupeGlobals(combined)\n    log('done', deduped.length)\n    return deduped\n  } finally {\n    client.close()\n  }\n}\n\n/**\n * @param {Pick<DecodeParams, 'toolPath' | 'elfPath'>} params\n * @param {DecodeOptions} [options={}] Default is `{}`\n * @returns {Promise<FrameVar[]>}\n */\nexport async function resolveGlobalSymbols(params, options = {}) {\n  const log = createGlobalsLogger(options.debug)\n  try {\n    if (params.toolPath.includes(xtensaLx106ToolHint)) {\n      log('skip globals for xtensa-lx106 gdb', params)\n      return []\n    }\n\n    const timeoutMs = getGlobalsTimeoutMs()\n    const controller = new AbortController()\n    let timedOut = false\n    const timeoutId = setTimeout(() => {\n      timedOut = true\n      controller.abort()\n    }, timeoutMs)\n\n    const onAbort = () => {\n      if (!controller.signal.aborted) {\n        controller.abort()\n      }\n    }\n    options.signal?.addEventListener('abort', onAbort)\n\n    log('resolve start', { timeoutMs })\n    try {\n      return await listGlobalSymbols(params, {\n        ...options,\n        signal: controller.signal,\n      })\n    } finally {\n      clearTimeout(timeoutId)\n      options.signal?.removeEventListener('abort', onAbort)\n      if (timedOut) {\n        log('resolve timeout', timeoutMs)\n      }\n    }\n  } catch (err) {\n    log('resolve error', err)\n    if (options.debug) {\n      options.debug('Failed to list global symbols:', err)\n    }\n    return []\n  }\n}\n","// @ts-check\n\nimport fs from 'node:fs/promises'\nimport os from 'node:os'\nimport path from 'node:path'\n\nimport { GdbMiClient, extractMiListContent } from './gdbMi.js'\nimport { resolveGlobalSymbols } from './globals.js'\nimport { toHexString } from './regs.js'\n\n/** @typedef {import('./decode.js').Debug} Debug */\n\nconst coredumpLogPrefix = '[trbr][coredump]'\n\n/**\n * @param {Debug | undefined} debug\n * @returns {Debug}\n */\nfunction createCoredumpLogger(debug) {\n  const writer =\n    debug ?? (process.env.TRBR_DEBUG === 'true' ? console.log : undefined)\n  return writer ? (...args) => writer(coredumpLogPrefix, ...args) : () => {}\n}\n\n/** @typedef {import('./decode.js').DecodeResult} DecodeResult */\n/** @typedef {import('./decode.js').DecodeInputFileSource} DecodeInputFileSource */\n/** @typedef {import('./decode.js').FrameArg} FrameArg */\n/** @typedef {import('./decodeParams.js').DecodeCoredumpParams} DecodeCoredumpParams */\n\n/**\n * Attempt to extract an embedded ELF from a raw ESP32 flash dump.\n *\n * @param {DecodeCoredumpParams} params\n * @param {Buffer} raw\n * @param {import('./decode.js').DecodeOptions} [options={}] Default is `{}`\n * @returns {Promise<CoredumpDecodeResult | undefined>}\n */\nasync function tryRawElfFallback(params, raw, options) {\n  const expectedMagic = Buffer.from([0x7f, 0x45, 0x4c, 0x46])\n  const offset = raw.indexOf(expectedMagic)\n  if (offset !== -1) {\n    // Estimate the total ELF size using program headers\n    const e_phoff = raw.readUInt32LE(offset + 28)\n    const e_phentsize = raw.readUInt16LE(offset + 42)\n    const e_phnum = raw.readUInt16LE(offset + 44)\n    const maxEnd = (() => {\n      let max = 0\n      for (let i = 0; i < e_phnum; i++) {\n        const entryOffset = offset + e_phoff + i * e_phentsize\n        const p_offset = raw.readUInt32LE(entryOffset + 4)\n        const p_filesz = raw.readUInt32LE(entryOffset + 16)\n        const end = p_offset + p_filesz\n        if (end > max) {\n          max = end\n        }\n      }\n      return max\n    })()\n    const elfTotalSize = maxEnd\n    if (raw.length >= offset + elfTotalSize) {\n      const elfBuffer = raw.subarray(offset, offset + elfTotalSize)\n      const tmpDirPath = await fs.mkdtemp(path.join(os.tmpdir(), 'trbr-'))\n      const extractedElfPath = path.join(tmpDirPath, 'extracted.elf')\n      await fs.writeFile(extractedElfPath, elfBuffer)\n      try {\n        const result = await decodeCoredump(\n          {\n            ...params,\n          },\n          { inputPath: extractedElfPath },\n          options,\n          false\n        )\n        return result\n      } finally {\n        await fs\n          .rm(tmpDirPath, { recursive: true, force: true })\n          .catch((err) => console.warn('Failed to clean up temp dir:', err))\n      }\n    }\n  }\n  return undefined\n}\n\n/**\n * @typedef {Object} ThreadDecodeResult\n * @property {string} threadId\n * @property {number} TCB\n * @property {string} [threadName]\n * @property {DecodeResult} result\n * @property {boolean} [current]\n */\n\n/** @typedef {ThreadDecodeResult[]} CoredumpDecodeResult */\n\n/**\n * Parses register values from MI output or \"info registers\" raw output.\n *\n * @param {string} regsRaw\n * @returns {Record<string, string>}\n */\nfunction parseRegisters(regsRaw) {\n  /** @type {Record<string, string>} */\n  const result = {}\n\n  // Try MI-style first: match optional frame-prefix then register-values\n  const miMatch = regsRaw.match(\n    /(?:frame=\\{[^}]*\\},)?register-values=\\[([^\\]]*)\\]/\n  )\n  if (miMatch) {\n    const inner = miMatch[1]\n    const regex = /\\{number=\"(\\d+)\",value=\"(0x[a-fA-F0-9]+)\"\\}/g\n    for (const m of inner.matchAll(regex)) {\n      result[m[1]] = m[2]\n    }\n    return result\n  }\n\n  // Try \"info registers\" style as fallback\n  const lines = regsRaw.split(/\\r?\\n/)\n  for (const line of lines) {\n    const match = line.match(/^~?\"?(\\w+)\\s+(0x[a-fA-F0-9]+)\\b/)\n    if (match) {\n      const [, name, value] = match\n      result[name] = value\n    }\n  }\n\n  return result\n}\n\n/**\n * @param {string} raw\n * @returns {Record<string, string>[]}\n */\nfunction parseBacktrace(raw) {\n  const entries = [...raw.matchAll(/frame=\\{([^}]+)\\}/g)].map((match) => {\n    /** @type {Record<string, string>} */\n    const obj = {}\n    for (const pair of match[1].split(',')) {\n      const [key, val] = pair.split('=')\n      obj[key] = val?.startsWith('\"') ? val.slice(1, -1) : val\n    }\n    return obj\n  })\n  return entries\n}\n\n/**\n * @param {string} str\n * @param {string} key\n * @returns {string | undefined}\n */\n/**\n * @param {DecodeCoredumpParams} params\n * @param {DecodeInputFileSource} input\n * @param {boolean} [tryRepair]\n * @param {import('./decode.js').DecodeOptions} [options={}] Default is `{}`\n * @returns {Promise<CoredumpDecodeResult>}\n */\nexport async function decodeCoredump(\n  params,\n  input,\n  options = {},\n  tryRepair = true\n) {\n  const { elfPath, toolPath } = params\n  const { inputPath } = input\n  const log = createCoredumpLogger(options.debug)\n  log('start', { toolPath, elfPath, inputPath })\n  const client = new GdbMiClient(\n    toolPath,\n    ['--interpreter=mi2', '-c', inputPath, elfPath],\n    options\n  )\n  /** @type {ThreadDecodeResult[]} */\n  const results = []\n\n  try {\n    // Use -thread-info for a more reliable MI listing of threads\n    await client.drainHandshake()\n    const globals = await resolveGlobalSymbols(params, options)\n    log('globals count', globals.length)\n\n    const threadsRaw = await client.sendCommand('-thread-info')\n    log('thread-info raw length', threadsRaw.length)\n\n    const currentThreadMatch = threadsRaw.match(/current-thread-id=\"(\\d+)\"/)\n    const currentThreadId = currentThreadMatch ? currentThreadMatch[1] : null\n\n    // Extract the contents of the top-level threads=[ ... ] block, handling nested brackets\n    const threadsContent = extractMiListContent(threadsRaw, 'threads')\n    /** @type {[string, string][]} */\n    const threadEntries = []\n    if (threadsContent) {\n      // Split into individual thread objects by balanced braces\n      const objs = []\n      let depth = 0\n      let objStart = -1\n      for (let i = 0; i < threadsContent.length; i++) {\n        const ch = threadsContent[i]\n        if (ch === '{') {\n          if (depth === 0) {\n            objStart = i\n          }\n          depth++\n        } else if (ch === '}') {\n          depth--\n          if (depth === 0 && objStart >= 0) {\n            objs.push(threadsContent.slice(objStart, i + 1))\n          }\n        }\n      }\n      // Extract id and TCB (target-id) from each object\n      for (const objStr of objs) {\n        const m = /id=\"([^\"]+)\"\\s*,\\s*target-id=\"process\\s+(\\d+)\"/.exec(objStr)\n        if (m) {\n          threadEntries.push([m[1], m[2]])\n        }\n      }\n    }\n    const threadIds = threadEntries.map(([id]) => id)\n    const threadTcbs = Object.fromEntries(\n      threadEntries.map(([id, tcb]) => [id, Number(tcb)])\n    )\n    log('threads parsed', { threadIds, threadTcbs })\n\n    for (const tid of threadIds) {\n      log('select thread', tid)\n      await client.sendCommand(`-thread-select ${tid}`)\n\n      const regNamesRaw = await client.sendCommand('-data-list-register-names')\n      const regNameMatch = regNamesRaw.match(/register-names=\\[(.*?)\\]/)\n      const regNames = regNameMatch\n        ? regNameMatch[1]\n            .split(',')\n            .map((s) => s.trim().replace(/^\"|\"$/g, ''))\n            .map((name, i) => [i.toString(), name])\n            .filter(([, name]) => !!name)\n        : []\n      const regNameMap = Object.fromEntries(regNames)\n\n      const regsOut = await client.sendCommand('-data-list-register-values x')\n      const parsedRegs = parseRegisters(regsOut)\n\n      const regsAsNamed = Object.fromEntries(\n        Object.entries(parsedRegs)\n          .map(([num, val]) => [regNameMap[num], Number(val)])\n          .filter(([name]) => !!name)\n      )\n      log('regs', tid, Object.keys(regsAsNamed))\n\n      const programCounter = regsAsNamed['pc']\n\n      const btOut = await client.sendCommand('-stack-list-frames')\n      log('stack frames raw length', btOut.length)\n\n      const argsOut = await client.sendCommand(\n        '-stack-list-arguments --simple-values 0 100'\n      )\n      log('stack args raw length', argsOut.length)\n      // Parse frame arguments safely, splitting on top-level frame boundaries\n      const argsListMatch = argsOut.match(/stack-args=\\[([\\s\\S]*)\\]/)\n      /** @type {{ level?: string; args: FrameArg[] }[]} */\n      let frameArgs = []\n      if (argsListMatch) {\n        const content = argsListMatch[1]\n        // Split on '},frame={' to avoid inner brace conflicts\n        const parts = content.split(/},\\s*frame=\\{/).map((part, idx) => {\n          if (idx === 0) {\n            return part + '}'\n          }\n          return 'frame={' + part + '}'\n        })\n        frameArgs = parts.map((frameStr) => {\n          const rawMatch = frameStr.match(/frame=\\{([\\s\\S]*)\\}/)\n          const raw = rawMatch ? rawMatch[1] : ''\n          /** @type {{ level?: string; args: FrameArg[] }} */\n          const obj = { args: [] }\n          // extract frame level\n          const levelMatch = raw.match(/level=\"(\\d+)\"/)\n          if (levelMatch) {\n            obj.level = levelMatch[1]\n          }\n          // extract args array content\n          const argsMatchInner = raw.match(/args=\\[([\\s\\S]*)\\]/)\n          if (argsMatchInner && argsMatchInner[1].trim()) {\n            const argsContent = argsMatchInner[1]\n            const argRegex =\n              /\\{name=\"([^\"]+)\",type=\"([^\"]+)\",value=\"([^\"]+)\"\\}/g\n            let m\n            while ((m = argRegex.exec(argsContent))) {\n              obj.args.push({ name: m[1], type: m[2], value: m[3] })\n            }\n          }\n          return obj\n        })\n      } else {\n        frameArgs = []\n      }\n\n      const btParsed = parseBacktrace(btOut)\n      const stacktraceLines = btParsed.map((frame, index) => {\n        const args = frameArgs[index]?.args || ''\n        return {\n          regAddr: frame.addr,\n          lineNumber: frame.line ?? '??',\n          ...(frame.func && frame.file\n            ? { method: frame.func, file: frame.file, args }\n            : {}),\n        }\n      })\n      log('stacktrace lines', tid, stacktraceLines.length)\n\n      results.push({\n        threadId: tid,\n        TCB: threadTcbs[tid],\n        result: {\n          faultInfo: {\n            coreId: parseInt(tid),\n            programCounter: {\n              addr: programCounter,\n              location: stacktraceLines[0] ?? {\n                regAddr: toHexString(programCounter),\n                lineNumber: '??',\n              },\n            },\n            faultCode: undefined, // Xtensa includes exccause, but the RISC-V variant does not include mcause, mtval, etc.\n          },\n          regs: regsAsNamed,\n          stacktraceLines,\n          globals,\n        },\n        current: tid === currentThreadId,\n      })\n    }\n  } finally {\n    client.close()\n  }\n\n  if (!results.length && tryRepair) {\n    const raw = await fs.readFile(input.inputPath)\n    const fallback = await tryRawElfFallback(params, raw)\n    if (fallback) {\n      return fallback\n    }\n  }\n\n  return results\n}\n","const __WEBPACK_NAMESPACE_OBJECT__ = require(\"node:net\");","// @ts-check\n\nimport net from 'node:net'\n\nimport { AbortError, neverSignal } from '../abort.js'\nimport { isRiscvTargetArch } from '../tool.js'\nimport { addr2line } from './addr2Line.js'\nimport {\n  GdbMiClient,\n  extractMiListContent,\n  parseMiResultRecord,\n  parseMiTupleList,\n  stripMiList,\n} from './gdbMi.js'\nimport { resolveGlobalSymbols } from './globals.js'\nimport { parseLines } from './regAddr.js'\nimport { toHexString } from './regs.js'\n\n// Based on the work of:\n//  - [Peter Dragun](https://github.com/peterdragun)\n//  - [Ivan Grokhotkov](https://github.com/igrr)\n//  - [suda-morris](https://github.com/suda-morris)\n//\n// https://github.com/espressif/esp-idf-monitor/blob/fae383ecf281655abaa5e65433f671e274316d10/esp_idf_monitor/gdb_panic_server.py\n\nconst riscvLogPrefix = '[trbr][riscv]'\n\n/**\n * @param {Debug | undefined} debug\n * @returns {Debug}\n */\nfunction createRiscvLogger(debug) {\n  const writer =\n    debug ?? (process.env.TRBR_DEBUG === 'true' ? console.log : undefined)\n  return writer ? (...args) => writer(riscvLogPrefix, ...args) : () => {}\n}\n\n/** @typedef {import('./decode.js').DecodeParams} DecodeParams */\n/** @typedef {import('./decode.js').DecodeResult} DecodeResult */\n/** @typedef {import('./decode.js').DecodeFunction} DecodeFunction */\n/** @typedef {import('./decode.js').DecodeOptions} DecodeOptions */\n/** @typedef {import('./decode.js').GDBLine} GDBLine */\n/** @typedef {import('./decode.js').ParsedGDBLine} ParsedGDBLine */\n/** @typedef {import('./decode.js').FrameArg} FrameArg */\n/** @typedef {import('./decode.js').FrameVar} FrameVar */\n/** @typedef {import('./decode.js').Debug} Debug */\n/** @typedef {import('./decode.js').RegAddr} RegAddr */\n/** @typedef {import('./decode.js').AddrLine} AddrLine */\n/** @typedef {import('./decode.js').PanicInfoWithStackData} PanicInfoWithStackData */\n/** @typedef {import('../tool.js').RiscvTargetArch} RiscvTargetArch */\nconst gdbRegsInfoRiscvIlp32 = /** @type {const} */ ([\n  'X0',\n  'RA',\n  'SP',\n  'GP',\n  'TP',\n  'T0',\n  'T1',\n  'T2',\n  'S0/FP',\n  'S1',\n  'A0',\n  'A1',\n  'A2',\n  'A3',\n  'A4',\n  'A5',\n  'A6',\n  'A7',\n  'S2',\n  'S3',\n  'S4',\n  'S5',\n  'S6',\n  'S7',\n  'S8',\n  'S9',\n  'S10',\n  'S11',\n  'T3',\n  'T4',\n  'T5',\n  'T6',\n  'MEPC', // where execution is happening (PC) and where it resumes after exception (MEPC).\n])\n\n/** @type {Record<RiscvTargetArch, DecodeFunction>} */\nexport const riscvDecoders = /** @type {const} */ ({\n  esp32c2: decodeRiscv,\n  esp32c3: decodeRiscv,\n  esp32c6: decodeRiscv,\n  esp32h2: decodeRiscv,\n  esp32h4: decodeRiscv,\n  esp32p4: decodeRiscv,\n})\n\n/** @type {Record<RiscvTargetArch, gdbRegsInfoRiscvIlp32>} */\nconst gdbRegsInfo = {\n  esp32c2: gdbRegsInfoRiscvIlp32,\n  esp32c3: gdbRegsInfoRiscvIlp32,\n  esp32c6: gdbRegsInfoRiscvIlp32,\n  esp32h2: gdbRegsInfoRiscvIlp32,\n  esp32h4: gdbRegsInfoRiscvIlp32,\n  esp32p4: gdbRegsInfoRiscvIlp32,\n}\n\n/**\n * @template {RiscvTargetArch} T\n * @param {T} type\n */\nfunction createRegNameValidator(type) {\n  const regsInfo = gdbRegsInfo[type]\n  if (!regsInfo) {\n    throw new Error(`Unsupported target: ${type}`)\n  }\n  /** @type {(regName: unknown) => regName is gdbRegsInfoRiscvIlp32} */\n  return (regName) =>\n    regsInfo.includes(\n      /** @type {(typeof gdbRegsInfoRiscvIlp32)[number]} */ (regName)\n    )\n}\n\n/**\n * @typedef {Object} RegisterDump\n * @property {number} coreId\n * @property {Record<string, number>} regs\n */\n\n/**\n * @typedef {Object} StackDump\n * @property {number} baseAddr\n * @property {number[]} data\n */\n\n/**\n * @typedef {Object} ParsePanicOutputParams\n * @property {string} input\n * @property {RiscvTargetArch} target\n */\n\n/**\n * @typedef {Object} ParsePanicOutputResult\n * @property {RegisterDump[]} regDumps\n * @property {StackDump[]} stackDump\n * @property {number} programCounter\n * @property {number} [faultCode]\n * @property {number} [faultAddr]\n */\n\n/**\n * @param {ParsePanicOutputParams} params\n * @returns {ParsePanicOutputResult}\n */\nfunction parse({ input, target }) {\n  const lines = input.split(/\\r?\\n|\\r/)\n  /** @type {RegisterDump[]} */\n  const regDumps = []\n  /** @type {StackDump[]} */\n  const stackDump = []\n  /** @type {RegisterDump | undefined} */\n  let currentRegDump\n  let inStackMemory = false\n  /** @type {number | undefined} */\n  let faultCode\n  /** @type {number | undefined} */\n  let faultAddr\n  let programCounter = 0\n\n  const regNameValidator = createRegNameValidator(target)\n\n  lines.forEach((line) => {\n    if (line.startsWith('Core')) {\n      const match = line.match(/^Core\\s+(\\d+)\\s+register dump:/)\n      if (match) {\n        currentRegDump = {\n          coreId: parseInt(match[1], 10),\n          regs: {},\n        }\n        regDumps.push(currentRegDump)\n      }\n    } else if (currentRegDump && !inStackMemory) {\n      const regMatches = line.matchAll(/([A-Z_0-9/]+)\\s*:\\s*(0x[0-9a-fA-F]+)/g)\n      for (const match of regMatches) {\n        const regName = match[1]\n        const regAddr = parseInt(match[2], 16)\n        if (regAddr && regNameValidator(regName)) {\n          currentRegDump.regs[regName] = regAddr\n          if (regName === 'MEPC') {\n            programCounter = regAddr // PC equivalent\n          }\n        } else if (regName === 'MCAUSE') {\n          faultCode = regAddr // EXCCAUSE equivalent\n        } else if (regName === 'MTVAL') {\n          faultAddr = regAddr // EXCVADDR equivalent\n        }\n      }\n      if (line.trim() === 'Stack memory:') {\n        inStackMemory = true\n      }\n    } else if (inStackMemory) {\n      const match = line.match(/^([0-9a-fA-F]+):\\s*((?:0x[0-9a-fA-F]+\\s*)+)/)\n      if (match) {\n        const baseAddr = parseInt(match[1], 16)\n        const data = match[2]\n          .trim()\n          .split(/\\s+/)\n          .map((hex) => parseInt(hex, 16))\n        stackDump.push({ baseAddr, data })\n      }\n    }\n  })\n\n  return { regDumps, stackDump, faultCode, faultAddr, programCounter }\n}\n\n/**\n * @typedef {Object} GetStackAddrAndDataParams\n * @property {StackDump[]} stackDump\n */\n\n/**\n * @typedef {Object} GetStackAddrAndDataResult\n * @property {number} stackBaseAddr\n * @property {Buffer} stackData\n */\n\n/**\n * @param {GetStackAddrAndDataParams} params\n * @returns {GetStackAddrAndDataResult}\n */\nfunction getStackAddrAndData({ stackDump }) {\n  let stackBaseAddr = 0\n  let baseAddr = 0\n  let bytesInLine = 0\n  let stackData = Buffer.alloc(0)\n\n  stackDump.forEach((line) => {\n    const prevBaseAddr = baseAddr\n    baseAddr = line.baseAddr\n    if (stackBaseAddr === 0) {\n      stackBaseAddr = baseAddr\n    } else {\n      if (baseAddr !== prevBaseAddr + bytesInLine) {\n        throw new Error('Invalid base address')\n      }\n    }\n\n    const lineData = Buffer.concat(\n      line.data.map((word) => {\n        const buf = Buffer.alloc(4)\n        // Stack memory is little-endian; preserve byte order for GDB reads.\n        buf.writeUInt32LE(word >>> 0)\n        return buf\n      })\n    )\n    bytesInLine = lineData.length\n    stackData = Buffer.concat([stackData, lineData])\n  })\n\n  return { stackBaseAddr, stackData }\n}\n\n/**\n * @typedef {Object} ParseIdfRiscvPanicOutputParams\n * @property {string} input\n * @property {RiscvTargetArch} target\n */\n\n/**\n * @param {ParseIdfRiscvPanicOutputParams} params\n * @returns {PanicInfoWithStackData}\n */\nfunction parsePanicOutput({ input, target }) {\n  const { regDumps, stackDump, programCounter, faultAddr, faultCode } = parse({\n    input,\n    target,\n  })\n  if (regDumps.length === 0) {\n    throw new Error('No register dumps found')\n  }\n  if (regDumps.length > 1) {\n    throw new Error('Handling of multi-core register dumps not implemented')\n  }\n\n  const { coreId, regs } = regDumps[0]\n  const { stackBaseAddr, stackData } = getStackAddrAndData({ stackDump })\n\n  return {\n    coreId,\n    programCounter,\n    faultAddr,\n    faultCode,\n    regs,\n    stackBaseAddr,\n    stackData,\n    target,\n  }\n}\n\n/**\n * @typedef {Object} GdbServerParams\n * @property {PanicInfoWithStackData} panicInfo\n * @property {Debug} [debug]\n */\n\n/**\n * @typedef {Object} StartGdbServerParams\n * @property {AbortSignal} [signal]\n */\n\nexport class GdbServer {\n  /** @param {GdbServerParams} params */\n  constructor(params) {\n    this.panicInfo = params.panicInfo\n    this.regList = gdbRegsInfo[params.panicInfo.target]\n    this.debug = params.debug ?? (() => {})\n  }\n\n  /**\n   * @param {StartGdbServerParams} [params]\n   * @returns {Promise<net.AddressInfo>}\n   */\n  async start(params = {}) {\n    if (this.server) {\n      throw new Error('Server already started')\n    }\n\n    const { signal = neverSignal } = params\n    const server = net.createServer()\n    this.server = server\n\n    await new Promise((resolve, reject) => {\n      const abortHandler = () => {\n        this.debug('User abort')\n        reject(new AbortError())\n        this.close()\n      }\n\n      if (signal.aborted) {\n        abortHandler()\n        return\n      }\n\n      signal.addEventListener('abort', abortHandler)\n      server.on('listening', () => {\n        signal.removeEventListener('abort', abortHandler)\n        resolve(undefined)\n      })\n      server.listen(0)\n    })\n\n    const address = server.address()\n    if (!address) {\n      this.close()\n      throw new Error('Failed to start server')\n    }\n    if (typeof address === 'string') {\n      this.close()\n      throw new Error(\n        `Expected an address info object. Got a string: ${address}`\n      )\n    }\n\n    server.on('connection', (socket) => {\n      let pending = ''\n      socket.on('data', (data) => {\n        pending = this._consumePackets(pending + data.toString(), socket)\n      })\n    })\n\n    return address\n  }\n\n  /**\n   * @param {string} pending\n   * @param {net.Socket} socket\n   * @returns {string}\n   */\n  _consumePackets(pending, socket) {\n    while (pending.length > 0) {\n      if (pending.startsWith('+')) {\n        pending = pending.slice(1)\n        continue\n      }\n\n      if (pending.startsWith('-')) {\n        this.debug(`Invalid command: ${pending}`)\n        socket.write('-')\n        socket.end()\n        return ''\n      }\n\n      const packetStart = pending.indexOf('$')\n      if (packetStart === -1) {\n        this.debug(`Discarding non-packet data: ${JSON.stringify(pending)}`)\n        return ''\n      }\n      if (packetStart > 0) {\n        const ignored = pending.slice(0, packetStart)\n        this.debug(`Discarding packet prefix: ${JSON.stringify(ignored)}`)\n        pending = pending.slice(packetStart)\n      }\n\n      const checksumMark = pending.indexOf('#', 1)\n      if (checksumMark === -1 || checksumMark + 2 >= pending.length) {\n        return pending\n      }\n\n      const packet = pending.slice(0, checksumMark + 3)\n      pending = pending.slice(checksumMark + 3)\n      this.debug(`Command: ${packet}`)\n      this._handleCommand(packet, socket)\n    }\n\n    return pending\n  }\n\n  close() {\n    this.server?.close()\n    this.server = undefined\n  }\n\n  /**\n   * @param {string} buffer\n   * @param {net.Socket} socket\n   */\n  _handleCommand(buffer, socket) {\n    if (buffer.startsWith('+')) {\n      buffer = buffer.slice(1) // ignore the leading '+'\n    }\n\n    const command = buffer.slice(1, -3) // ignore checksums\n    // Acknowledge the command\n    socket.write('+')\n    this.debug(\n      `Raw buffer (length ${buffer.length}): ${JSON.stringify(buffer)}`\n    )\n    this.debug(`Got command: ${command}`)\n    if (command === '?') {\n      // report sigtrap as the stop reason; the exact reason doesn't matter for backtracing\n      this.debug('Responding with: T05')\n      this._respond('T05', socket)\n    } else if (command.startsWith('Hg') || command.startsWith('Hc')) {\n      // Select thread command\n      this.debug('Responding with: OK')\n      this._respond('OK', socket)\n    } else if (command === 'qfThreadInfo') {\n      // Get list of threads.\n      // Only one thread for now, can be extended to show one thread for each core,\n      // if we dump both cores (e.g. on an interrupt watchdog)\n      this.debug('Responding with: m1')\n      this._respond('m1', socket)\n    } else if (command === 'qC') {\n      // That single thread is selected.\n      this.debug('Responding with: QC1')\n      this._respond('QC1', socket)\n    } else if (command === 'g') {\n      // Registers read\n      this._respondRegs(socket)\n    } else if (command.startsWith('m')) {\n      // Memory read\n      const [addr, size] = command\n        .slice(1)\n        .split(',')\n        .map((v) => parseInt(v, 16))\n      this._respondMem(addr, size, socket)\n    } else if (command.startsWith('vKill') || command === 'k') {\n      // Quit\n      this.debug('Responding with: OK')\n      this._respond('OK', socket)\n      socket.end()\n    } else {\n      // Empty response required for any unknown command\n      this.debug('Responding with: (empty)')\n      this._respond('', socket)\n    }\n  }\n\n  /**\n   * @param {string} data\n   * @param {net.Socket} socket\n   */\n  _respond(data, socket) {\n    // calculate checksum\n    const dataBytes = Buffer.from(data, 'ascii')\n    const checksum = dataBytes.reduce((sum, byte) => sum + byte, 0) & 0xff\n    // format and write the response\n    const res = `$${data}#${checksum.toString(16).padStart(2, '0')}`\n    socket.write(res)\n    this.debug(`Wrote: ${res}`)\n  }\n\n  /** @param {net.Socket} socket */\n  _respondRegs(socket) {\n    let response = ''\n    // https://github.com/espressif/esp-idf-monitor/blob/fae383ecf281655abaa5e65433f671e274316d10/esp_idf_monitor/gdb_panic_server.py#L242-L247\n    // It loops over the list of register names.\n    // For each register name, it gets the register value from panicInfo.regs.\n    // It converts the register value to bytes in little-endian byte order.\n    // It converts each byte to a hexadecimal string and joins them together.\n    // It appends the hexadecimal string to the response string.\n    for (const regName of this.regList) {\n      const regVal = this.panicInfo.regs[regName] || 0\n      const regBytes = Buffer.alloc(4)\n      regBytes.writeUInt32LE(regVal)\n      const regValHex = regBytes.toString('hex')\n      response += regValHex\n    }\n    this.debug(\n      `Register values: ${this.regList\n        .map((r) => `${r}=${toHexString(this.panicInfo.regs[r] || 0)}`)\n        .join(', ')}`\n    )\n    this.debug(`Register response: ${response}`)\n    this._respond(response, socket)\n  }\n\n  /**\n   * @param {number} startAddr\n   * @param {number} size\n   * @param {net.Socket} socket\n   */\n  _respondMem(startAddr, size, socket) {\n    const stackAddrMin = this.panicInfo.stackBaseAddr\n    const stackData = this.panicInfo.stackData\n    const stackLen = stackData.length\n    const stackAddrMax = stackAddrMin + stackLen\n\n    const inStack = (/** @type {number} */ addr) =>\n      stackAddrMin <= addr && addr < stackAddrMax\n\n    let result = ''\n    for (let addr = startAddr; addr < startAddr + size; addr++) {\n      if (!inStack(addr)) {\n        result += '00'\n      } else {\n        result += stackData[addr - stackAddrMin].toString(16).padStart(2, '0')\n      }\n    }\n\n    this.debug(\n      `Memory read request from 0x${startAddr.toString(16)} for ${size} bytes`\n    )\n    this.debug(`Responding with memory: ${result}`)\n    this._respond(result, socket)\n  }\n}\n\nconst miErrorPattern = /^\\^error/m\n\n/**\n * @param {string} raw\n * @returns {string | undefined}\n */\nfunction parseMiErrorMessage(raw) {\n  const match = raw.match(/\\^error(?:,[^\\n]*?msg=\"((?:\\\\.|[^\"])*)\")?/m)\n  if (!match?.[1]) {\n    return undefined\n  }\n  return match[1]\n    .replace(/\\\\\\\\/g, '\\\\')\n    .replace(/\\\\\"/g, '\"')\n    .replace(/\\\\n/g, '\\n')\n}\n\n/**\n * @param {string} raw\n * @returns {string}\n */\nfunction summarizeMiOutput(raw) {\n  const normalized = raw\n    .split(/\\r?\\n/)\n    .map((line) => line.trim())\n    .filter(Boolean)\n    .join(' ')\n  if (!normalized) {\n    return 'empty MI response'\n  }\n  const maxLength = 240\n  if (normalized.length <= maxLength) {\n    return normalized\n  }\n  return `${normalized.slice(0, maxLength)}...[truncated ${normalized.length - maxLength} chars]`\n}\n\n/**\n * @param {string} raw\n * @returns {string}\n */\nfunction describeMiFailure(raw) {\n  return parseMiErrorMessage(raw) ?? summarizeMiOutput(raw)\n}\n\n/**\n * @param {DecodeOptions | undefined} options\n * @returns {boolean}\n */\nfunction shouldIncludeFrameVars(options) {\n  return options?.includeFrameVars === true\n}\n\n/**\n * @param {Record<string, string>} tuple\n * @returns {FrameArg | undefined}\n */\nfunction toFrameArg(tuple) {\n  if (!tuple.name) {\n    return undefined\n  }\n  /** @type {FrameArg} */\n  const arg = { name: tuple.name }\n  if (tuple.type) {\n    arg.type = tuple.type\n  }\n  if (tuple.value !== undefined) {\n    arg.value = tuple.value\n  }\n  return arg\n}\n\n/**\n * @param {Record<string, string>} tuple\n * @param {'local' | 'argument' | 'global'} scope\n * @returns {FrameVar | undefined}\n */\nfunction toFrameVar(tuple, scope) {\n  if (!tuple.name) {\n    return undefined\n  }\n  /** @type {FrameVar} */\n  const variable = { scope, name: tuple.name }\n  if (tuple.type) {\n    variable.type = tuple.type\n  }\n  if (tuple.value !== undefined) {\n    variable.value = tuple.value\n  }\n  if (tuple.addr || tuple.address) {\n    variable.address = tuple.addr || tuple.address\n  }\n  return variable\n}\n\n/**\n * @param {Record<string, string>} frame\n * @returns {GDBLine | ParsedGDBLine}\n */\nfunction toParsedFrame(frame) {\n  const regAddr = frame.addr || '??'\n  const method = frame.func && frame.func !== '??' ? frame.func : undefined\n  const fileRaw = frame.fullname || frame.file\n  const file = fileRaw && fileRaw !== '??' ? fileRaw : undefined\n  const lineNumber = frame.line && frame.line !== '??' ? frame.line : undefined\n\n  if (!method && !file && !lineNumber) {\n    return { regAddr, lineNumber: '??' }\n  }\n\n  return {\n    regAddr,\n    method: method || '??',\n    file: file || '??',\n    lineNumber: lineNumber || '??',\n  }\n}\n\n/**\n * @param {string} raw\n * @returns {Record<string, string>[]}\n */\nfunction parseMiFrames(raw) {\n  const listContent = extractMiListContent(raw, 'stack')\n  return parseMiTupleList(listContent, 'frame')\n}\n\n/**\n * @template T\n * @param {T | undefined} value\n * @returns {value is T}\n */\nfunction isDefined(value) {\n  return value !== undefined\n}\n\n/**\n * @param {string} raw\n * @param {string} frameLevel\n * @returns {FrameArg[] | undefined}\n */\nfunction parseMiStackArgs(raw, frameLevel) {\n  if (miErrorPattern.test(raw)) {\n    return undefined\n  }\n  const listContent = extractMiListContent(raw, 'stack-args')\n  if (listContent === undefined) {\n    return undefined\n  }\n  const frames = parseMiTupleList(listContent, 'frame')\n  const frame = frames.find((entry) => entry.level === frameLevel) ?? frames[0]\n  if (!frame || !frame.args) {\n    return []\n  }\n  const argsList = stripMiList(frame.args) ?? ''\n  return parseMiTupleList(argsList).map(toFrameArg).filter(isDefined)\n}\n\n/**\n * @param {string} raw\n * @returns {FrameVar[] | undefined}\n */\nfunction parseMiLocals(raw) {\n  if (miErrorPattern.test(raw)) {\n    return undefined\n  }\n  const listContent = extractMiListContent(raw, 'variables')\n  if (listContent === undefined) {\n    return undefined\n  }\n  return parseMiTupleList(listContent)\n    .map((tuple) => toFrameVar(tuple, 'local'))\n    .filter(isDefined)\n}\n\n/**\n * @param {string} name\n * @returns {string}\n */\nfunction stripEntrySuffix(name) {\n  return name.replace(/@entry$/, '')\n}\n\n/**\n * @param {FrameArg[]} [args]\n * @returns {Set<string>}\n */\nfunction collectArgNames(args) {\n  const names = new Set()\n  if (!args) {\n    return names\n  }\n  for (const arg of args) {\n    if (!arg?.name) {\n      continue\n    }\n    names.add(arg.name)\n    names.add(stripEntrySuffix(arg.name))\n  }\n  return names\n}\n\n/**\n * @param {FrameArg[]} [args]\n * @returns {FrameArg[]}\n */\nfunction dedupeArgs(args) {\n  if (!args || !args.length) {\n    return []\n  }\n  /** @type {Map<string, { arg: FrameArg; fromEntry: boolean }>} */\n  const byName = new Map()\n  /** @type {string[]} */\n  const order = []\n\n  for (const arg of args) {\n    if (!arg?.name) {\n      continue\n    }\n    const baseName = stripEntrySuffix(arg.name)\n    const fromEntry = arg.name.endsWith('@entry')\n    const existing = byName.get(baseName)\n    if (!existing) {\n      byName.set(baseName, { arg: { ...arg, name: baseName }, fromEntry })\n      order.push(baseName)\n      continue\n    }\n\n    if (existing.fromEntry && !fromEntry) {\n      byName.set(baseName, { arg: { ...arg, name: baseName }, fromEntry })\n      continue\n    }\n\n    if (!existing.arg.type && arg.type) {\n      existing.arg.type = arg.type\n    }\n    if (\n      (!existing.arg.value || existing.arg.value === '<optimized out>') &&\n      arg.value &&\n      arg.value !== '<optimized out>'\n    ) {\n      existing.arg.value = arg.value\n    }\n  }\n\n  return order\n    .map((name) => byName.get(name))\n    .filter(isDefined)\n    .map((entry) => entry.arg)\n}\n\n/**\n * @param {FrameVar[]} locals\n * @param {FrameArg[]} [args]\n * @returns {FrameVar[]}\n */\nfunction filterArgLocals(locals, args) {\n  const argNames = collectArgNames(args)\n  if (!argNames.size) {\n    return locals\n  }\n  return locals.filter((local) => {\n    if (!local?.name) {\n      return false\n    }\n    const name = local.name\n    return !argNames.has(name) && !argNames.has(stripEntrySuffix(name))\n  })\n}\n\n/**\n * @param {string} type\n * @returns {string}\n */\nfunction normalizeType(type) {\n  return type\n    .replace(/\\bconst\\b/g, '')\n    .replace(/\\bvolatile\\b/g, '')\n    .replace(/\\bstatic\\b/g, '')\n    .replace(/\\s+/g, ' ')\n    .trim()\n}\n\n/**\n * @param {string} type\n * @returns {boolean}\n */\nfunction isPrimitiveType(type) {\n  const cleaned = normalizeType(type)\n    .replace(/\\bstruct\\b|\\bclass\\b|\\bunion\\b|\\benum\\b/g, '')\n    .trim()\n  return /^(unsigned|signed)?\\s*(char|short|int|long|long long|float|double|bool|size_t|uintptr_t|intptr_t|uint\\d+_t|int\\d+_t)$/.test(\n    cleaned\n  )\n}\n\n/**\n * @param {FrameVar} variable\n * @returns {boolean}\n */\nfunction shouldExpandVar(variable) {\n  const type = variable.type\n  if (!type) {\n    return false\n  }\n  if (/\\[.*\\]/.test(type)) {\n    return true\n  }\n  if (type.includes('*') || type.includes('&')) {\n    return false\n  }\n  if (/\\bstruct\\b|\\bclass\\b|\\bunion\\b/.test(type)) {\n    return true\n  }\n  return !isPrimitiveType(type)\n}\n\n/**\n * @param {string} value\n * @returns {string}\n */\nfunction quoteMiArg(value) {\n  const escaped = value.replace(/\\\\/g, '\\\\\\\\').replace(/\"/g, '\\\\\"')\n  return `\"${escaped}\"`\n}\n\n/**\n * @param {Record<string, string>} tuple\n * @returns {FrameVar | undefined}\n */\n/**\n * @typedef {Object} VarChildEntry\n * @property {string} [varObject]\n * @property {number} numChildren\n * @property {FrameVar} variable\n */\n\n/**\n * @param {Record<string, string>} tuple\n * @returns {VarChildEntry | undefined}\n */\nfunction toVarChildEntry(tuple) {\n  const displayName = tuple.exp || tuple.name\n  if (!displayName) {\n    return undefined\n  }\n  /** @type {FrameVar} */\n  const variable = { name: displayName }\n  if (tuple.type) {\n    variable.type = tuple.type\n  }\n  if (tuple.value !== undefined) {\n    variable.value = tuple.value\n  }\n  return {\n    varObject: tuple.name,\n    numChildren: parseInt(tuple.numchild ?? '0', 10),\n    variable,\n  }\n}\n\n/**\n * @param {GdbMiClient} client\n * @param {string} expression\n * @returns {Promise<string | undefined>}\n */\nasync function evaluateExpression(client, expression) {\n  const raw = await client.sendCommand(\n    `-data-evaluate-expression ${quoteMiArg(expression)}`\n  )\n  if (miErrorPattern.test(raw)) {\n    return undefined\n  }\n  const record = parseMiResultRecord(raw)\n  return record.value\n}\n\n/**\n * @param {GdbMiClient} client\n * @param {string} varObject\n * @returns {Promise<VarChildEntry[] | undefined>}\n */\nasync function listVarChildren(client, varObject) {\n  const raw = await client.sendCommand(\n    `-var-list-children --simple-values ${varObject}`\n  )\n  if (miErrorPattern.test(raw)) {\n    return undefined\n  }\n  const listContent = extractMiListContent(raw, 'children')\n  if (listContent === undefined) {\n    return undefined\n  }\n  return parseMiTupleList(listContent, 'child')\n    .map(toVarChildEntry)\n    .filter(isDefined)\n}\n\n/**\n * @param {string} name\n * @returns {boolean}\n */\nfunction isAccessSpecifier(name) {\n  return name === 'public' || name === 'private' || name === 'protected'\n}\n\n/**\n * @param {GdbMiClient} client\n * @param {string} varObject\n * @param {{ maxChildren: number; maxDepth: number }} options\n * @param {number} depth\n * @param {Set<string>} visited\n * @returns {Promise<FrameVar[]>}\n */\nasync function expandVarObjectChildren(\n  client,\n  varObject,\n  options,\n  depth,\n  visited\n) {\n  if (!varObject || depth > options.maxDepth) {\n    return []\n  }\n  if (visited.has(varObject)) {\n    return []\n  }\n  visited.add(varObject)\n\n  const children = await listVarChildren(client, varObject)\n  if (!children || !children.length) {\n    return []\n  }\n\n  /** @type {FrameVar[]} */\n  const result = []\n\n  for (const entry of children) {\n    if (!entry) {\n      continue\n    }\n    const variable = entry.variable\n    const childVarObject = entry.varObject\n\n    if (isAccessSpecifier(variable.name)) {\n      if (childVarObject && depth < options.maxDepth) {\n        const expanded = await expandVarObjectChildren(\n          client,\n          childVarObject,\n          options,\n          depth + 1,\n          visited\n        )\n        for (const child of expanded) {\n          result.push(child)\n          if (result.length >= options.maxChildren) {\n            return result.slice(0, options.maxChildren)\n          }\n        }\n      }\n      continue\n    }\n\n    if (\n      childVarObject &&\n      entry.numChildren > 0 &&\n      depth < options.maxDepth &&\n      shouldExpandVar(variable)\n    ) {\n      variable.children = await expandVarObjectChildren(\n        client,\n        childVarObject,\n        options,\n        depth + 1,\n        visited\n      )\n    }\n\n    result.push(variable)\n    if (result.length >= options.maxChildren) {\n      return result.slice(0, options.maxChildren)\n    }\n  }\n\n  return result\n}\n\n/**\n * @param {GdbMiClient} client\n * @param {FrameVar} variable\n * @param {{ maxChildren: number; maxDepth: number }} options\n * @returns {Promise<void>}\n */\nasync function expandVariable(client, variable, options) {\n  const expression = variable.name\n  const createRaw = await client.sendCommand(\n    `-var-create - * ${quoteMiArg(expression)}`\n  )\n  if (miErrorPattern.test(createRaw)) {\n    return\n  }\n  const record = parseMiResultRecord(createRaw)\n  const varObject = record.name\n  const numChildren = parseInt(record.numchild ?? '0', 10)\n  if (variable.value === undefined || variable.value === '<optimized out>') {\n    if (record.value !== undefined) {\n      variable.value = record.value\n    } else {\n      const evaluated = await evaluateExpression(client, expression)\n      if (evaluated !== undefined) {\n        variable.value = evaluated\n      }\n    }\n  }\n  if (varObject) {\n    try {\n      if (numChildren > 0) {\n        const children = await expandVarObjectChildren(\n          client,\n          varObject,\n          { maxChildren: options.maxChildren, maxDepth: options.maxDepth },\n          0,\n          new Set()\n        )\n        if (children.length) {\n          variable.children = children\n        }\n      }\n    } finally {\n      await client.sendCommand(`-var-delete ${varObject}`)\n    }\n  }\n}\n\n/**\n * @param {GdbMiClient} client\n * @param {FrameVar[]} locals\n * @param {Debug} log\n * @returns {Promise<FrameVar[]>}\n */\nasync function expandLocals(client, locals, log) {\n  const maxVars = 12\n  const maxChildren = 16\n  const maxDepth = 3\n  let expanded = 0\n  for (const variable of locals) {\n    if (!shouldExpandVar(variable) || expanded >= maxVars) {\n      continue\n    }\n    expanded += 1\n    try {\n      await expandVariable(client, variable, { maxChildren, maxDepth })\n    } catch (error) {\n      log('expand variable failed', variable.name, error)\n    }\n  }\n  return locals\n}\n\n/**\n * @param {DecodeParams} params\n * @param {PanicInfoWithStackData} panicInfo\n * @param {DecodeOptions} options\n * @param {Debug} [log]\n * @returns {Promise<(GDBLine | ParsedGDBLine)[]>}\n */\nasync function fetchStacktraceWithMi(\n  params,\n  panicInfo,\n  options = {},\n  log = createRiscvLogger(options.debug)\n) {\n  const { elfPath, toolPath } = params\n  const includeFrameVars = shouldIncludeFrameVars(options)\n  let server\n  /** @type {GdbMiClient | undefined} */\n  let client\n\n  try {\n    log('fetch stacktrace start', { elfPath, toolPath })\n    const { signal, debug } = options\n    const gdbServer = new GdbServer({ panicInfo, debug })\n    const { port } = await gdbServer.start({ signal })\n    server = gdbServer\n    log('gdb server started', { port })\n\n    client = new GdbMiClient(\n      toolPath,\n      ['--interpreter=mi2', '-n', elfPath],\n      options\n    )\n    await client.drainHandshake()\n    const targetResult = await client.sendCommand(\n      `-target-select remote :${port}`\n    )\n    if (miErrorPattern.test(targetResult)) {\n      throw new Error(\n        `Failed to connect to GDB remote target: ${describeMiFailure(targetResult)}`\n      )\n    }\n    log('gdb remote connected')\n\n    const framesRaw = await client.sendCommand('-stack-list-frames')\n    if (miErrorPattern.test(framesRaw)) {\n      throw new Error(\n        `Failed to list stack frames: ${describeMiFailure(framesRaw)}`\n      )\n    }\n    const frames = parseMiFrames(framesRaw)\n    const stacktraceLines = frames.map(toParsedFrame)\n    log('frames parsed', frames.length)\n    frames.forEach((frame, index) => {\n      log('frame', index, frame)\n    })\n\n    for (let i = 0; i < frames.length; i++) {\n      const frameLevel = frames[i].level ?? `${i}`\n      log('select frame', frameLevel)\n      await client.sendCommand(`-stack-select-frame ${frameLevel}`)\n\n      const argsRaw = await client.sendCommand(\n        `-stack-list-arguments --simple-values ${frameLevel} ${frameLevel}`\n      )\n      const rawArgs = parseMiStackArgs(argsRaw, frameLevel)\n      const args = rawArgs ? dedupeArgs(rawArgs) : undefined\n      const parsedFrame =\n        'method' in stacktraceLines[i]\n          ? /** @type {ParsedGDBLine} */ (stacktraceLines[i])\n          : undefined\n      if (args !== undefined && parsedFrame) {\n        parsedFrame.args = args.length ? args : []\n        log('frame args', frameLevel, parsedFrame.args)\n      }\n\n      if (includeFrameVars) {\n        const localsRaw = await client.sendCommand(\n          '-stack-list-variables --simple-values'\n        )\n        let locals = parseMiLocals(localsRaw)\n        if (locals !== undefined && parsedFrame) {\n          locals = filterArgLocals(locals, args)\n          locals = await expandLocals(client, locals, log)\n          parsedFrame.locals = locals.length ? locals : []\n          log('frame locals', frameLevel, parsedFrame.locals)\n        }\n      }\n    }\n\n    log('fetch stacktrace done', stacktraceLines.length)\n    return stacktraceLines\n  } finally {\n    client?.close()\n    server?.close()\n  }\n}\n\nconst exceptions = [\n  { code: 0x0, description: 'Instruction address misaligned' },\n  { code: 0x1, description: 'Instruction access fault' },\n  { code: 0x2, description: 'Illegal instruction' },\n  { code: 0x3, description: 'Breakpoint' },\n  { code: 0x4, description: 'Load address misaligned' },\n  { code: 0x5, description: 'Load access fault' },\n  { code: 0x6, description: 'Store/AMO address misaligned' },\n  { code: 0x7, description: 'Store/AMO access fault' },\n  { code: 0x8, description: 'Environment call from U-mode' },\n  { code: 0x9, description: 'Environment call from S-mode' },\n  { code: 0xb, description: 'Environment call from M-mode' },\n  { code: 0xc, description: 'Instruction page fault' },\n  { code: 0xd, description: 'Load page fault' },\n  { code: 0xf, description: 'Store/AMO page fault' },\n]\n\n/**\n * @param {string} elfPath\n * @param {number} port\n * @returns {string[]}\n */\nfunction buildPanicServerArgs(elfPath, port) {\n  return [\n    '--batch',\n    '-n',\n    elfPath,\n    // '-ex', // executes a command\n    // `set remotetimeout ${debug ? 300 : 2}`, // Set the timeout limit to wait for the remote target to respond to num seconds. The default is 2 seconds. (https://sourceware.org/gdb/current/onlinedocs/gdb.html/Remote-Configuration.html)\n    '-ex',\n    `target remote :${port}`, // https://sourceware.org/gdb/current/onlinedocs/gdb.html/Server.html#Server\n    '-ex',\n    'bt',\n  ]\n}\n\n/**\n * @param {DecodeParams} params\n * @param {PanicInfoWithStackData} panicInfo\n * @param {DecodeOptions} options\n * @param {Debug} [log]\n * @returns {Promise<(GDBLine | ParsedGDBLine)[]>}\n */\nasync function processPanicOutput(\n  params,\n  panicInfo,\n  options = {},\n  log = createRiscvLogger(options.debug)\n) {\n  return fetchStacktraceWithMi(params, panicInfo, options, log)\n}\n\n/**\n * @param {PanicInfoWithStackData} panicInfo\n * @param {AddrLine} programCounter\n * @param {AddrLine | undefined} faultAddr\n * @param {(GDBLine | ParsedGDBLine)[]} stacktraceLines\n * @param {FrameVar[]} [globals]\n * @returns {DecodeResult}\n */\nfunction createDecodeResult(\n  panicInfo,\n  programCounter,\n  faultAddr,\n  stacktraceLines,\n  globals\n) {\n  const exception = exceptions.find((e) => e.code === panicInfo.faultCode)\n\n  return {\n    faultInfo: {\n      coreId: panicInfo.coreId,\n      programCounter,\n      faultAddr,\n      faultCode: panicInfo.faultCode,\n      faultMessage: exception ? exception.description : undefined,\n    },\n    regs: panicInfo.regs,\n    stacktraceLines,\n    allocInfo: undefined,\n    globals,\n  }\n}\n\n/** @type {import('./decode.js').DecodeFunction} */\nexport async function decodeRiscv(params, input, options) {\n  const log = createRiscvLogger(options?.debug)\n  const target = params.targetArch\n  if (!isRiscvTargetArch(target)) {\n    throw new Error(`Unsupported target: ${target}`)\n  }\n  log('decode start', { target, inputType: typeof input })\n\n  /** @type {Exclude<typeof input, string>} */\n  let panicInfo\n  if (typeof input === 'string') {\n    panicInfo = parsePanicOutput({\n      input,\n      target,\n    })\n  } else {\n    panicInfo = input\n  }\n\n  if ('backtraceAddrs' in panicInfo) {\n    throw new Error(\n      'Unexpectedly received a panic info with backtrace addresses for RISC-V'\n    )\n  }\n  log('panic info', {\n    coreId: panicInfo.coreId,\n    programCounter: panicInfo.programCounter,\n    faultAddr: panicInfo.faultAddr,\n    faultCode: panicInfo.faultCode,\n  })\n\n  const includeFrameVars = shouldIncludeFrameVars(options)\n  const [stacktraceLines, [programCounter, faultAdd], globals] =\n    await Promise.all([\n      processPanicOutput(params, panicInfo, options, log),\n      addr2line(\n        params,\n        [panicInfo.programCounter, panicInfo.faultAddr],\n        options\n      ),\n      includeFrameVars\n        ? resolveGlobalSymbols(params, options)\n        : Promise.resolve([]),\n    ])\n  if (!includeFrameVars) {\n    log('skip globals/locals (includeFrameVars=false)')\n  }\n  log('addr2line done', { programCounter, faultAdd })\n  log('globals count', globals.length)\n  stacktraceLines.forEach((line, index) => {\n    log('stacktrace line', index, line)\n  })\n\n  return createDecodeResult(\n    panicInfo,\n    programCounter,\n    faultAdd,\n    stacktraceLines,\n    globals\n  )\n}\n\n/** (non-API) */\nexport const __tests = /** @type {const} */ ({\n  createRegNameValidator,\n  parsePanicOutput,\n  buildPanicServerArgs,\n  processPanicOutput,\n  parseMiFrames,\n  parseMiStackArgs,\n  parseMiLocals,\n  toParsedFrame,\n  toHexString,\n  parseGDBOutput: parseLines,\n  getStackAddrAndData,\n  gdbRegsInfoRiscvIlp32,\n  gdbRegsInfo,\n  createDecodeResult,\n})\n","// @ts-check\n\nimport { addr2line } from './addr2Line.js'\nimport { isGDBLine } from './decode.js'\nimport { resolveGlobalSymbols } from './globals.js'\nimport {\n  parseESP32PanicOutput,\n  parseESP8266PanicOutput,\n} from './xtensaPanicParse.js'\n\nconst xtensaLogPrefix = '[trbr][xtensa]'\n\n/**\n * @param {import('./decode.js').Debug | undefined} debug\n * @returns {import('./decode.js').Debug}\n */\nfunction createXtensaLogger(debug) {\n  const writer =\n    debug ?? (process.env.TRBR_DEBUG === 'true' ? console.log : undefined)\n  return writer ? (...args) => writer(xtensaLogPrefix, ...args) : () => {}\n}\n\n/** @typedef {import('./decode.js').DecodeParams} DecodeParams */\n/** @typedef {import('./decode.js').DecodeResult} DecodeResult */\n/** @typedef {import('./decode.js').DecodeOptions} DecodeOptions */\n/** @typedef {import('./decode.js').GDBLine} GDBLine */\n/** @typedef {import('./decode.js').ParsedGDBLine} ParsedGDBLine */\n/** @typedef {import('./decode.js').Debug} Debug */\n\n/**\n * @param {DecodeOptions | undefined} options\n * @returns {boolean}\n */\nfunction shouldIncludeFrameVars(options) {\n  return options?.includeFrameVars === true\n}\n\n/** @type {import('./decode.js').DecodeFunction} */\nexport async function decodeXtensa(params, input, options) {\n  const logXtensa = createXtensaLogger(options?.debug)\n  logXtensa('decode start', {\n    targetArch: params.targetArch,\n    inputType: typeof input,\n  })\n  /** @type {Exclude<typeof input, string>} */\n  let panicInfo\n  if (typeof input === 'string') {\n    panicInfo = parseESP32PanicOutput(input)\n    if (\n      !Object.keys(panicInfo.regs).length &&\n      !panicInfo.backtraceAddrs.length\n    ) {\n      panicInfo = parseESP8266PanicOutput(input)\n    }\n  } else {\n    panicInfo = input\n  }\n\n  if ('stackBaseAddr' in panicInfo) {\n    console.error('input contains stackBaseAddr', JSON.stringify(panicInfo))\n    throw new Error('panicInfo must not contain stackBaseAddr')\n  }\n\n  const includeFrameVars = shouldIncludeFrameVars(options)\n  const [globals, decodedAddrs] = await Promise.all([\n    includeFrameVars\n      ? resolveGlobalSymbols(params, options)\n      : Promise.resolve([]),\n    addr2line(\n      params,\n      [\n        panicInfo.programCounter,\n        panicInfo.faultAddr,\n        ...(panicInfo.backtraceAddrs ?? []),\n      ],\n      options\n    ),\n  ])\n  if (!includeFrameVars) {\n    logXtensa('skip globals (includeFrameVars=false)')\n  }\n  logXtensa('globals count', globals.length)\n  const [programCounter, faultAddr, ...addrLines] = decodedAddrs\n  logXtensa('addr2line done', {\n    programCounter,\n    faultAddr,\n    frames: addrLines.length,\n  })\n  let faultMessage\n  if (panicInfo.faultCode) {\n    faultMessage = exceptions[panicInfo.faultCode]\n  }\n\n  /** @type {import('./decode.js').FaultInfo} */\n  const faultInfo = {\n    coreId: panicInfo.coreId,\n    programCounter,\n    faultAddr,\n    faultCode: panicInfo.faultCode,\n    faultMessage,\n  }\n\n  return {\n    faultInfo,\n    regs: panicInfo.regs,\n    stacktraceLines: addrLines\n      .map(({ location }) => location)\n      .filter(isGDBLine),\n    allocInfo: undefined,\n    globals,\n  }\n}\n\n// Taken from https://github.com/me-no-dev/EspExceptionDecoder/blob/ff4fc36bdaf0bfd6e750086ac01554867ede76d3/src/EspExceptionDecoder.java#L59-L90\nconst reserved = 'reserved'\nconst exceptions = [\n  'Illegal instruction',\n  'SYSCALL instruction',\n  'InstructionFetchError: Processor internal physical address or data error during instruction fetch',\n  'LoadStoreError: Processor internal physical address or data error during load or store',\n  'Level1Interrupt: Level-1 interrupt as indicated by set level-1 bits in the INTERRUPT register',\n  \"Alloca: MOVSP instruction, if caller's registers are not in the register file\",\n  'IntegerDivideByZero: QUOS, QUOU, REMS, or REMU divisor operand is zero',\n  reserved,\n  'Privileged: Attempt to execute a privileged operation when CRING ? 0',\n  'LoadStoreAlignmentCause: Load or store to an unaligned address',\n  reserved,\n  reserved,\n  'InstrPIFDataError: PIF data error during instruction fetch',\n  'LoadStorePIFDataError: Synchronous PIF data error during LoadStore access',\n  'InstrPIFAddrError: PIF address error during instruction fetch',\n  'LoadStorePIFAddrError: Synchronous PIF address error during LoadStore access',\n  'InstTLBMiss: Error during Instruction TLB refill',\n  'InstTLBMultiHit: Multiple instruction TLB entries matched',\n  'InstFetchPrivilege: An instruction fetch referenced a virtual address at a ring level less than CRING',\n  reserved,\n  'InstFetchProhibited: An instruction fetch referenced a page mapped with an attribute that does not permit instruction fetch',\n  reserved,\n  reserved,\n  reserved,\n  'LoadStoreTLBMiss: Error during TLB refill for a load or store',\n  'LoadStoreTLBMultiHit: Multiple TLB entries matched for a load or store',\n  'LoadStorePrivilege: A load or store referenced a virtual address at a ring level less than CRING',\n  reserved,\n  'LoadProhibited: A load referenced a page mapped with an attribute that does not permit loads',\n  'StoreProhibited: A store referenced a page mapped with an attribute that does not permit stores',\n]\n\nexport { parseESP32PanicOutput, parseESP8266PanicOutput }\n\n/** (non-API) */\nexport const __tests = /** @type {const} */ ({\n  exceptions,\n  decodeAddrs: addr2line,\n  parseESP32PanicOutput,\n  parseESP8266PanicOutput,\n})\n","// @ts-check\n\nimport fs from 'node:fs/promises'\nimport os from 'node:os'\nimport path from 'node:path'\nimport { pipeline } from 'node:stream/promises'\n\nimport { AbortError } from '../abort.js'\nimport { addr2line } from './addr2Line.js'\nimport { decodeCoredump } from './coredump.js'\nimport { texts } from './decode.text.js'\nimport { isCoredumpModeParams } from './decodeParams.js'\nimport { riscvDecoders } from './riscv.js'\nimport { decodeXtensa } from './xtensa.js'\n\n/** @typedef {import('./decodeParams.js').DecodeParams} DecodeParams */\n/** @typedef {import('./decodeParams.js').DecodeCoredumpParams} DecodeCoredumpParams */\n\n/** @typedef {string} RegAddr `'0x12345678'` or `'this::loop'` */\n\n/**\n * @typedef {Object} GDBLine\n * @property {RegAddr} regAddr\n * @property {string} lineNumber `'36'` or `'??'`\n */\n\n/**\n * @typedef {Object} FrameArg\n * @property {string} name - When name and value are absent, type is the name\n * @property {string} [type]\n * @property {string} [value]\n */\n\n/**\n * @typedef {Object} FrameVar\n * @property {string} name\n * @property {string} [type]\n * @property {string} [value]\n * @property {string} [address]\n * @property {FrameVar[]} [children]\n * @property {'local' | 'argument' | 'global'} [scope]\n */\n\n/**\n * @typedef {GDBLine & {\n *   file: string\n *   method: string\n *   args?: FrameArg[]\n *   locals?: FrameVar[]\n *   globals?: FrameVar[]\n * }} ParsedGDBLine\n */\n\n/** @typedef {RegAddr | GDBLine | ParsedGDBLine} AddrLocation */\n\n/**\n * @typedef {Object} AddrLine\n * @property {number} [addr]\n * @property {AddrLocation} location\n */\n\n/**\n * @param {unknown} arg\n * @returns {arg is AddrLine}\n */\nexport function isAddrLine(arg) {\n  return (\n    arg !== null &&\n    typeof arg === 'object' &&\n    'addr' in arg &&\n    (typeof arg.addr === 'number' || arg.addr === undefined) &&\n    'location' in arg &&\n    (typeof arg.location === 'string' ||\n      isGDBLine(arg.location) ||\n      isParsedGDBLine(arg.location))\n  )\n}\n\n/** @param {AddrLocation} [addrLocation] */\n// TODO: is it needed?\nexport function getAddr(addrLocation) {\n  if (!addrLocation) {\n    return undefined\n  }\n  const parsedAddr = parseInt(\n    isGDBLine(addrLocation) ? addrLocation.regAddr : (addrLocation ?? '0'),\n    16\n  )\n  return isNaN(parsedAddr) ? undefined : parsedAddr\n}\n\n/** @param {AddrLocation} addrLocation */\nexport function stringifyAddr(addrLocation) {\n  if (isParsedGDBLine(addrLocation)) {\n    return `${addrLocation.regAddr} in ${addrLocation.method} at ${addrLocation.file}:${addrLocation.lineNumber}`\n  }\n  if (isGDBLine(addrLocation)) {\n    return `${addrLocation.regAddr} in ${addrLocation.lineNumber}`\n  }\n  return `${addrLocation} in ?? ()`\n}\n\n/**\n * @callback DecodeFunction\n * @param {DecodeParams} params\n * @param {DecodeFunctionInput} input\n * @param {DecodeOptions} [options]\n * @returns {Promise<DecodeResult>}\n */\n\n/**\n * @typedef {Object} DecodeInputFileSource\n * @property {string} inputPath\n */\n\n/**\n * @typedef {Object} DecodeInputStreamSource\n * @property {NodeJS.ReadableStream} inputStream\n */\n\n/**\n * @param {unknown} arg\n * @returns {arg is DecodeInputFileSource}\n */\nexport function isDecodeInputFileSource(arg) {\n  return (\n    arg !== null &&\n    typeof arg === 'object' &&\n    'inputPath' in arg &&\n    typeof arg.inputPath === 'string'\n  )\n}\n\n/**\n * @param {unknown} arg\n * @returns {arg is DecodeInputStreamSource}\n */\nexport function isDecodeInputStreamSource(arg) {\n  return (\n    arg !== null &&\n    typeof arg === 'object' &&\n    'inputStream' in arg &&\n    arg.inputStream instanceof require('stream').Readable\n  )\n}\n\n/** @typedef {Awaited<ReturnType<DecodeCoredumpFunction>>[number] | string} DecodeFunctionInput */\n\n/**\n * @typedef {DecodeInputFileSource\n *   | DecodeInputStreamSource\n *   | DecodeFunctionInput} DecodeInput\n */\n\n/**\n * @typedef {Object} AllocInfo\n * @property {AddrLocation} allocAddr\n * @property {number} allocSize\n */\n\n/**\n * @typedef {Object} FaultInfo\n * @property {number} coreId\n * @property {AddrLine} programCounter PC at fault (PC for ESP32, MEPC for\n *   RISC-V, EPC1 for ESP8266)\n * @property {AddrLine} [faultAddr] EXCVADDR for ESP32, EXCVADDR for RISC-V and\n *   ESP8266\n * @property {number} [faultCode] EXCCAUSE for ESP32, EXCCODE for RISC-V\n * @property {string} [faultMessage]\n */\n\n/**\n * @typedef {Object} DecodeResult\n * @property {FaultInfo} [faultInfo]\n * @property {Record<string, number>} [regs]\n * @property {(GDBLine | ParsedGDBLine)[]} stacktraceLines\n * @property {AllocInfo} [allocInfo]\n * @property {FrameVar[]} [globals]\n */\n\n/**\n * @typedef {Object} DecodeOptions\n * @property {AbortSignal} [signal]\n * @property {Debug} [debug]\n * @property {boolean} [includeFrameVars] Enables heavy variable collection\n *   (locals/globals). Default is `false`.\n */\n\n/**\n * @callback Debug\n * @param {any} formatter\n * @param {...any} args\n * @returns {void}\n */\n\n/**\n * @typedef {Object} PanicInfo\n * @property {number} coreId\n * @property {number} [programCounter]\n * @property {number} [faultAddr]\n * @property {number} [faultCode]\n * @property {Record<string, number>} regs\n */\n\n/**\n * @typedef {PanicInfo & {\n *   stackBaseAddr: number\n *   stackData: Buffer\n *   target: keyof typeof riscvDecoders\n * }} PanicInfoWithStackData\n */\n\n/**\n * @typedef {PanicInfo & {\n *   backtraceAddrs: (AddrLine | number)[]\n * }} PanicInfoWithBacktrace\n */\n\n/**\n * @callback DecodeCoredumpFunction\n * @param {DecodeParams} params\n * @param {string} coredumpInput\n * @param {DecodeOptions} options\n * @returns {Promise<(PanicInfoWithBacktrace | PanicInfoWithStackData)[]>}\n */\n\nexport const defaultTargetArch = /** @type {const} */ ('xtensa')\n\n/** @typedef {import('../tool.js').DecodeTarget} DecodeTarget */\n\nconst envDebugEnabled = process.env.TRBR_DEBUG === 'true'\nconst decodeLogPrefix = '[trbr][decode]'\n\n/**\n * @param {Debug | undefined} debug\n * @returns {Debug}\n */\nfunction createDecodeLogger(debug) {\n  const writer = debug ?? (envDebugEnabled ? console.log : undefined)\n  return writer ? (...args) => writer(decodeLogPrefix, ...args) : () => {}\n}\n\nconst decoders = /** @type {const} */ ({\n  [defaultTargetArch]: decodeXtensa,\n  ...riscvDecoders,\n})\n\nexport const arches = /** @type {DecodeTarget[]} */ (Object.keys(decoders))\n\n/**\n * @param {unknown} arg\n * @returns {arg is DecodeTarget}\n */\nexport function isDecodeTarget(arg) {\n  return typeof arg === 'string' && arg in decoders\n}\n\n/**\n * @param {DecodeParams} params\n * @param {DecodeInput} decodeInput\n * @param {DecodeOptions} options\n * @returns {Promise<\n *   DecodeResult | import('./coredump.js').CoredumpDecodeResult\n * >}\n */\nexport async function decode(\n  params,\n  decodeInput,\n  options = { debug: () => {}, signal: new AbortController().signal }\n) {\n  const log = createDecodeLogger(options?.debug)\n  log('start', {\n    targetArch: params?.targetArch,\n    coredumpMode: isCoredumpModeParams(params),\n    inputType: typeof decodeInput,\n  })\n  /** @type {(() => Promise<unknown>)[]} */\n  const toDispose = []\n\n  try {\n    if (isCoredumpModeParams(params)) {\n      let coredumpInput\n      if (isDecodeInputFileSource(decodeInput)) {\n        coredumpInput = decodeInput.inputPath\n      } else if (isDecodeInputStreamSource(decodeInput)) {\n        const tmpDirPath = await fs.mkdtemp(path.join(os.tmpdir(), 'trbr-'))\n        coredumpInput = path.join(tmpDirPath, 'coredump.elf')\n        toDispose.push(async () => {\n          try {\n            await fs.rm(tmpDirPath, { recursive: true, force: true })\n          } catch (err) {\n            console.error('Failed to delete temporary coredump directory:', err)\n          }\n        })\n        const fd = await fs.open(coredumpInput, 'w')\n        /** @type {import('node:fs').WriteStream | undefined} */\n        let target\n        try {\n          target = fd.createWriteStream()\n          await pipeline(decodeInput.inputStream, target)\n        } finally {\n          Promise.allSettled([\n            fd.close(),\n            new Promise((resolve, reject) =>\n              target?.close((err) => {\n                if (err) {\n                  reject(err)\n                } else {\n                  resolve(undefined)\n                }\n              })\n            ),\n          ]).then((cleanupTasks) =>\n            cleanupTasks.forEach((task) => {\n              if (task.status === 'rejected') {\n                console.error('Failed to close stream:', task.reason)\n              }\n            })\n          )\n        }\n      }\n      if (!coredumpInput) {\n        throw new Error(\n          `Could not determine coredump path from input: ${JSON.stringify(\n            decodeInput\n          )}`\n        )\n      }\n\n      const result = await decodeCoredump(\n        params,\n        { inputPath: coredumpInput },\n        options\n      )\n\n      return result.map((threadDecodeResult) => ({\n        ...threadDecodeResult,\n        ...fixDecodeResult(threadDecodeResult.result),\n      }))\n    }\n\n    const { targetArch } = params\n    const decoder = decoders[targetArch]\n    if (!decoder) {\n      throw new Error(texts.unsupportedTargetArch(targetArch))\n    }\n\n    /** @type {DecodeFunctionInput} */\n    let input\n    if (typeof decodeInput === 'string') {\n      input = decodeInput\n    } else if (isDecodeInputFileSource(decodeInput)) {\n      input = await fs.readFile(decodeInput.inputPath, 'utf8')\n    } else if (isDecodeInputStreamSource(decodeInput)) {\n      input = ''\n      for await (const chunk of decodeInput.inputStream) {\n        input = chunk.toString()\n      }\n    } else {\n      input = decodeInput\n    }\n\n    const result = await decoder(params, input, options)\n    const fixedResult = fixDecodeResult(result)\n    if (options.signal?.aborted) {\n      throw new AbortError()\n    }\n    return fixedResult\n  } catch (err) {\n    if (err instanceof Error && 'code' in err && err.code === 'ABORT_ERR') {\n      throw new AbortError()\n    }\n    throw err\n  } finally {\n    for (const dispose of toDispose) {\n      try {\n        await dispose()\n      } catch (err) {\n        console.error('Failed to dispose resource:', err)\n      }\n    }\n  }\n}\n\n/** @param {DecodeResult} result */\nfunction fixDecodeResult(result) {\n  const fixedPathsResult = fixWindowsPaths(result)\n  let filteredResult = filterFreeRTOSStackLines(fixedPathsResult)\n  filteredResult = filterStackPointerLines(filteredResult) // let users decide if they want to filter stack pointer lines\n  const fixedFaultInfoResult = fixFaultInfo(filteredResult)\n  const dedupedResult = dedupeGDBLines(fixedFaultInfoResult)\n  return dedupedResult\n}\n\n/**\n * @param {unknown} arg\n * @returns {arg is GDBLine}\n */\nexport function isGDBLine(arg) {\n  return (\n    arg !== null &&\n    typeof arg === 'object' &&\n    'regAddr' in arg &&\n    typeof arg.regAddr === 'string' &&\n    'lineNumber' in arg &&\n    typeof arg.lineNumber === 'string'\n  )\n}\n\n/**\n * @param {unknown} arg\n * @returns {arg is ParsedGDBLine}\n */\nexport function isParsedGDBLine(arg) {\n  return (\n    isGDBLine(arg) &&\n    'file' in arg &&\n    typeof arg.file === 'string' &&\n    'method' in arg &&\n    typeof arg.method === 'string'\n  )\n}\n\n/**\n * @param {DecodeResult} result\n * @returns {DecodeResult}\n */\nfunction fixWindowsPaths(result) {\n  return {\n    ...result,\n    faultInfo: result.faultInfo\n      ? {\n          ...result.faultInfo,\n          programCounter: fixWindowsPathInLocation(\n            result.faultInfo.programCounter\n          ),\n          faultAddr: fixWindowsPathInLocation(result.faultInfo.faultAddr),\n        }\n      : undefined,\n    stacktraceLines: result.stacktraceLines.map(fixWindowsPathInLocation),\n    allocInfo: result.allocInfo\n      ? {\n          ...result.allocInfo,\n          allocAddr: fixWindowsPathInLocation(result.allocInfo.allocAddr),\n        }\n      : undefined,\n  }\n}\n\n/**\n * @template {AddrLine | AddrLocation | undefined} T\n * @param {T} locationAware\n * @returns {T}\n */\nfunction fixWindowsPathInLocation(locationAware) {\n  if (!locationAware) {\n    return locationAware\n  }\n\n  if (isAddrLine(locationAware)) {\n    const location = locationAware.location\n    if (isParsedGDBLine(location)) {\n      const copy = JSON.parse(JSON.stringify(locationAware))\n      copy.location.file = fixWindowsPath(location.file)\n      return copy\n    }\n  }\n\n  if (isParsedGDBLine(locationAware)) {\n    const copy = JSON.parse(JSON.stringify(locationAware))\n    copy.file = fixWindowsPath(locationAware.file)\n    return copy\n  }\n\n  return locationAware\n}\n\n// To fix the path separator issue on Windows:\n//      -      \"file\": \"D:\\\\a\\\\esp-exception-decoder\\\\esp-exception-decoder\\\\src\\\\test\\\\sketches\\\\riscv_1/riscv_1.ino\"\n//      +      \"file\": \"d:\\\\a\\\\esp-exception-decoder\\\\esp-exception-decoder\\\\src\\\\test\\\\sketches\\\\riscv_1\\\\riscv_1.ino\"\n/** @param {string} path */\nfunction fixWindowsPath(path) {\n  return process.platform === 'win32' && /^[a-zA-Z]:\\\\/.test(path)\n    ? path.replace(/\\//g, '\\\\')\n    : path\n}\n\n/** (non-API) */\nexport const __tests = /** @type {const} */ ({\n  fixWindowsPath,\n  fixWindowsPaths,\n})\n\n/**\n * Debug utility to log all decoded address info using addr2line.\n *\n * @param {string} toolPath\n * @param {string} elfPath\n * @param {number[]} rawAddresses\n */\nexport async function debugAllAddrs(toolPath, elfPath, rawAddresses) {\n  const lines = await addr2line({ toolPath, elfPath }, rawAddresses)\n  console.log('Decoded Addresses:')\n  console.log('done')\n  console.log('----------------------')\n  const padding = String(lines.length - 1).length\n  console.log(\n    lines\n      .map((line) => line.location)\n      .map(stringifyAddr)\n      .map(\n        (line, index) => `#${index.toString().padStart(padding, ' ')} ${line}`\n      )\n      .join('\\n')\n  )\n  console.log('----------------------')\n}\n\n/**\n * @param {GDBLine | ParsedGDBLine} left\n * @param {GDBLine | ParsedGDBLine} right\n */\nfunction equalsGDBLine(left, right) {\n  if (isParsedGDBLine(left) && !isParsedGDBLine(right)) {\n    return false\n  }\n  if (!isParsedGDBLine(left) && isParsedGDBLine(right)) {\n    return false\n  }\n\n  if (isParsedGDBLine(left) && isParsedGDBLine(right)) {\n    return (\n      left.regAddr === right.regAddr &&\n      left.lineNumber === right.lineNumber &&\n      left.file === right.file &&\n      left.method === right.method\n    )\n  }\n\n  return left.regAddr === right.regAddr && left.lineNumber === right.lineNumber\n}\n\n/**\n * @param {DecodeResult} result\n * @returns\n */\nfunction filterFreeRTOSStackLines(result) {\n  return {\n    ...result,\n    stacktraceLines: result.stacktraceLines.filter((line) => {\n      if (\n        isGDBLine(line) &&\n        line.lineNumber === '??' &&\n        line.regAddr.toLowerCase() === '0xfeefeffe'\n      ) {\n        return false\n      }\n      return true\n    }),\n  }\n}\n\n/**\n * @param {DecodeResult} result\n * @returns {DecodeResult}\n */\nfunction filterStackPointerLines(result) {\n  return {\n    ...result,\n    stacktraceLines: result.stacktraceLines.reduce(\n      (acc, currentLine, index, thisArray) => {\n        const prevLine = thisArray[index - 1]\n        if (prevLine && isStackPointerLine(currentLine, prevLine)) {\n          return acc\n        }\n        return [...acc, currentLine]\n      },\n      /** @type {(GDBLine | ParsedGDBLine)[]} */ ([])\n    ),\n  }\n}\n\n/**\n * @param {GDBLine | ParsedGDBLine} line\n * @param {GDBLine | ParsedGDBLine} prevLine\n * @returns\n */\nfunction isStackPointerLine(line, prevLine) {\n  if (!isParsedGDBLine(prevLine)) {\n    return false\n  }\n\n  const prevAddr = getAddr(prevLine.regAddr)\n  const addr = getAddr(line.regAddr)\n  if (addr === undefined || prevAddr === undefined) {\n    return false\n  }\n\n  const isAddr3x = addr >>> 28 === 0x3\n  const isPrevAddr4x = prevAddr >>> 28 === 0x4\n\n  return line.lineNumber === '??' && isAddr3x && isPrevAddr4x\n}\n\n/**\n * @param {DecodeResult} result\n * @returns {DecodeResult}\n */\nfunction dedupeGDBLines(result) {\n  return {\n    ...result,\n    stacktraceLines: result.stacktraceLines.reduce(\n      (acc, currentLine, index) => {\n        const previousLine = acc[index - 1]\n        if (previousLine && equalsGDBLine(previousLine, currentLine)) {\n          return acc\n        }\n        return [...acc, currentLine]\n      },\n      /** @type {(GDBLine | ParsedGDBLine)[]} */ ([])\n    ),\n  }\n}\n\n/**\n * @param {DecodeResult} result\n * @returns {DecodeResult}\n */\nfunction fixFaultInfo(result) {\n  if (\n    result.faultInfo &&\n    isGDBLine(result.faultInfo.faultAddr?.location) &&\n    result.faultInfo.faultAddr.location.lineNumber === '??' &&\n    !result.faultInfo.faultAddr.addr\n  ) {\n    // removes {regAddr: '0x00000000', lineNumber: '??'}\n    const copy = JSON.parse(JSON.stringify(result))\n    delete copy.faultInfo.faultAddr\n    return copy\n  }\n\n  return result\n}\n","// @ts-check\n\nexport const texts = {\n  unsupportedTargetArch: (/** @type {string} */ targetArch) =>\n    `Unsupported decode target: ${targetArch}`,\n}\n","// @ts-check\n\nimport {\n  defaultTargetArch,\n  findTargetArch,\n  resolveBuildProperties,\n  resolveToolPath,\n} from '../tool.js'\n\n/** @typedef {import('../tool.js').DecodeTarget} DecodeTarget */\n/** @typedef {import('fqbn').FQBN} FQBN */\n\n// --- Provides\n\n/**\n * @typedef {Object} DecodeParams\n * @property {string} toolPath\n * @property {string} elfPath\n * @property {DecodeTarget} targetArch\n */\n\n/** @typedef {DecodeParams & CoredumpMode} DecodeCoredumpParams */\n\n// --- Base\n\n/**\n * @typedef {Object} CreateDecodeParamsParams\n * @property {string} elfPath\n */\n\n/**\n * @typedef {Object} ArduinoCliParams\n * @property {string} arduinoCliPath\n * @property {string} [arduinoCliConfigPath]\n * @property {string} [additionalUrls]\n */\n\n/**\n * @typedef {Object} ToolParams\n * @property {string} toolPath\n * @property {DecodeTarget} [targetArch]\n */\n\n/**\n * @typedef {Object} CoredumpMode\n * @property {true} coredumpMode\n */\n\n/**\n * @typedef {Object} BacktraceMode\n * @property {false} [coredumpMode]\n */\n\n/**\n * @typedef {Object} WithFQBN\n * @property {FQBN} fqbn\n */\n\n/**\n * @typedef {WithFQBN & {\n *   buildProperties: Record<string, string>\n * }} WithBuildProperties\n */\n\n// --- Backtrace\n\n/** @typedef {CreateDecodeParamsParams & ToolParams & BacktraceMode} CreateDecodeParamsFromToolParams */\n/**\n * @typedef {CreateDecodeParamsParams &\n *   ArduinoCliParams &\n *   WithFQBN &\n *   BacktraceMode} CreateDecodeParamsFromFQBNParams\n */\n/** @typedef {CreateDecodeParamsParams & WithBuildProperties & BacktraceMode} CreateDecodeParamsFromBuildPropertiesParams */\n/**\n * @typedef {CreateDecodeParamsFromToolParams\n *   | CreateDecodeParamsFromFQBNParams\n *   | CreateDecodeParamsFromBuildPropertiesParams} CreateDecodeParamsFromParams\n */\n\n/**\n * @callback CreateDecodeParams\n * @param {CreateDecodeParamsFromParams} params\n * @returns {Promise<DecodeParams>}\n */\n\n// --- Coredump\n\n/** @typedef {CreateDecodeParamsParams & ToolParams & CoredumpMode} CreateCoredumpDecodeParamsFromToolParams */\n/**\n * @typedef {CreateDecodeParamsParams &\n *   ArduinoCliParams &\n *   WithFQBN &\n *   CoredumpMode} CreateCoredumpDecodeParamsFromFQBNParams\n */\n/** @typedef {CreateDecodeParamsParams & WithBuildProperties & CoredumpMode} CreateCoredumpDecodeParamsFromBuildPropertiesParams */\n/**\n * @typedef {CreateCoredumpDecodeParamsFromToolParams\n *   | CreateCoredumpDecodeParamsFromFQBNParams\n *   | CreateCoredumpDecodeParamsFromBuildPropertiesParams} CreateCoredumpDecodeParamsFromParams\n */\n\n/**\n * @callback CreateCoredumpDecodeParams\n * @param {CreateCoredumpDecodeParamsFromParams} params\n * @returns {Promise<DecodeCoredumpParams>}\n */\n\n/**\n * @param {CreateDecodeParamsParams} params\n * @returns {params is CreateCoredumpDecodeParamsFromParams}\n */\nexport function isCoredumpModeParams(params) {\n  return 'coredumpMode' in params && Boolean(params.coredumpMode)\n}\n\n/**\n * @param {CreateDecodeParamsParams} params\n * @returns {params is CreateDecodeParamsFromToolParams|CreateCoredumpDecodeParamsFromToolParams}\n */\nfunction isToolPathParams(params) {\n  return 'toolPath' in params && typeof params.toolPath === 'string'\n}\n\n/**\n * @param {CreateDecodeParamsParams} params\n * @returns {params is CreateDecodeParamsFromBuildPropertiesParams|CreateCoredumpDecodeParamsFromBuildPropertiesParams}\n */\nfunction isBuildPropertiesParams(params) {\n  return (\n    'buildProperties' in params && typeof params.buildProperties === 'object'\n  )\n}\n\n/**\n * @param {CreateDecodeParamsParams} params\n * @returns {params is CreateDecodeParamsFromFQBNParams|CreateCoredumpDecodeParamsFromFQBNParams}\n */\nfunction isArduinoCliParams(params) {\n  return 'arduinoCliPath' in params && typeof params.arduinoCliPath === 'string'\n}\n\n/**\n * @overload\n * @param {CreateDecodeParamsFromParams} params\n * @returns {Promise<DecodeParams>}\n */\n/**\n * @overload\n * @param {CreateCoredumpDecodeParamsFromParams} params\n * @returns {Promise<DecodeCoredumpParams>}\n */\n/**\n * @param {CreateDecodeParamsFromParams\n *   | CreateCoredumpDecodeParamsFromParams} params\n * @returns {Promise<DecodeParams | DecodeCoredumpParams>}\n */\nexport async function createDecodeParams(params) {\n  /** @type {string | undefined} */\n  let toolPath\n  /** @type {DecodeTarget | undefined} */\n  let targetArch\n\n  if (isToolPathParams(params)) {\n    toolPath = params.toolPath\n    targetArch = params.targetArch ?? defaultTargetArch\n  } else if (isBuildPropertiesParams(params)) {\n    toolPath = await resolveToolPath(params)\n    targetArch = findTargetArch(params)\n  } else if (isArduinoCliParams(params)) {\n    const buildProperties = await resolveBuildProperties(params)\n    toolPath = await resolveToolPath({\n      fqbn: params.fqbn,\n      buildProperties,\n    })\n    targetArch = findTargetArch({ buildProperties })\n  } else {\n    throw new Error(\n      `Unexpected create decode params input: ${JSON.stringify(params)}`\n    )\n  }\n\n  /** @type {DecodeParams} */\n  const decodeParams = {\n    elfPath: params.elfPath,\n    toolPath,\n    targetArch,\n  }\n\n  if (!isCoredumpModeParams(params)) {\n    return decodeParams\n  }\n\n  return { ...decodeParams, coredumpMode: true }\n}\n","// @ts-check\n\n/**\n * @param {string} input\n * @returns {import('./decode.js').PanicInfoWithBacktrace}\n */\nexport function parseESP8266PanicOutput(input) {\n  const lines = input.split(/\\r?\\n|\\r/)\n  /** @type {Record<string, number>} */\n  const regs = {}\n  const coreId = 0\n  /** @type {number[]} */\n  const backtraceAddrs = []\n  /** @type {number | undefined} */\n  let faultCode\n  /** @type {number | undefined} */\n  let faultAddr\n\n  const regLine = input.match(/Exception\\s+\\((\\d+)\\)/)\n  if (regLine) {\n    faultCode = parseInt(regLine[1], 10)\n  }\n\n  for (const line of lines) {\n    const epcMatches = line.matchAll(\n      /(epc\\d+|excvaddr|depc)=(0x[0-9a-fA-F]{8})/g\n    )\n    for (const match of epcMatches) {\n      const [, reg, hex] = match\n      regs[reg.toUpperCase()] = parseInt(hex, 16)\n      if (reg.toLowerCase() === 'excvaddr') {\n        faultAddr = parseInt(hex, 16)\n      }\n    }\n\n    // Example line: 3fff10b0:  4021a5d4 00000033 3fff20dc 40201ed3\n    const stackMatch = line.match(/^\\s*[0-9a-f]{8}:\\s+((?:[0-9a-f]{8}\\s*)+)/i)\n    if (stackMatch) {\n      const words = stackMatch[1].trim().split(/\\s+/)\n      for (const word of words) {\n        const addr = parseInt(word, 16)\n        if (!Number.isNaN(addr) && addr & 0x40000000) {\n          backtraceAddrs.push(addr)\n        }\n      }\n    }\n  }\n\n  return {\n    coreId,\n    regs,\n    backtraceAddrs,\n    faultCode,\n    faultAddr,\n    programCounter: regs.EPC1,\n  }\n}\n\n/**\n * @param {string} input\n * @returns {import('./decode.js').PanicInfoWithBacktrace}\n */\nexport function parseESP32PanicOutput(input) {\n  const lines = input.split(/\\r?\\n|\\r/)\n  /** @type {Record<string, number>} */\n  const regs = {}\n  let coreId = 0\n  /** @type {number[]} */\n  const backtraceAddrs = []\n  const coreIdMatch = input.match(/Guru Meditation Error: Core\\s+(\\d+)/)\n  if (coreIdMatch) {\n    coreId = parseInt(coreIdMatch[1], 10)\n  }\n\n  const regRegex = /([A-Z]+[0-9]*)\\s*:\\s*(0x[0-9a-fA-F]+)/g\n  for (const line of lines) {\n    for (const match of line.matchAll(regRegex)) {\n      const [, regName, hexValue] = match\n      const value = parseInt(hexValue, 16)\n      if (!Number.isNaN(value)) {\n        regs[regName] = value\n      }\n    }\n\n    if (line.startsWith('Backtrace:')) {\n      const matches = Array.from(line.matchAll(/0x[0-9a-fA-F]{8}/g))\n      for (const match of matches) {\n        const addr = parseInt(match[0], 16)\n        if (!Number.isNaN(addr)) {\n          backtraceAddrs.push(addr)\n        }\n      }\n    }\n  }\n\n  return {\n    coreId,\n    regs,\n    backtraceAddrs,\n    faultCode: regs.EXCCAUSE,\n    faultAddr: regs.EXCVADDR,\n    programCounter: regs.PC,\n  }\n}\n","// @ts-check\n\n/** @param {string} filename */\nexport function appendDotExeOnWindows(filename) {\n  return `${filename}${process.platform === 'win32' ? '.exe' : ''}`\n}\n","// @ts-check\n\nimport fs from 'node:fs/promises'\nimport path from 'node:path'\n\nimport { exec } from './exec.js'\nimport { appendDotExeOnWindows } from './os.js'\n\n/**\n * @typedef {Object} FindTooPathParams\n * @property {string} arduinoCliPath\n * @property {import('fqbn').FQBN} fqbn\n * @property {string} [arduinoCliConfigPath]\n * @property {string} [additionalUrls]\n */\n\n/**\n * @param {FindTooPathParams} params\n * @param {import('./decode/decode.js').DecodeOptions} [options]\n */\nexport async function findToolPath(\n  { arduinoCliPath, fqbn, arduinoCliConfigPath, additionalUrls },\n  options\n) {\n  const buildProperties = await resolveBuildProperties(\n    {\n      arduinoCliPath,\n      fqbn,\n      additionalUrls,\n      arduinoCliConfigPath,\n    },\n    options\n  )\n  return resolveToolPath({ fqbn, buildProperties })\n}\n\n/**\n * @param {FindTooPathParams} params\n * @param {import('./decode/decode.js').DecodeOptions} [options]\n */\nexport async function resolveBuildProperties(\n  { arduinoCliPath, fqbn, arduinoCliConfigPath, additionalUrls },\n  options\n) {\n  const { stdout } = await execBoardDetails({\n    arduinoCliPath,\n    fqbn,\n    arduinoCliConfigPath,\n    additionalUrls,\n    signal: options?.signal,\n  })\n\n  const { build_properties } = JSON.parse(stdout)\n  return parseBuildProperties(build_properties)\n}\n\n/**\n * @typedef {Object} FindTargetArchParams\n * @property {Record<string, string>} buildProperties\n */\n\nconst riscTargetArchs = /** @type {const} */ ([\n  'esp32c2',\n  'esp32c3',\n  'esp32c6',\n  'esp32h2',\n  'esp32h4', // XXX: there is no such build.mcu in the latest (3.2.1) ESP32 core for Arduino (https://github.com/espressif/esp-idf-monitor/blob/fae383ecf281655abaa5e65433f671e274316d10/esp_idf_monitor/gdb_panic_server.py#L63),\n  'esp32p4',\n])\nexport const defaultTargetArch = /** @type {const} */ ('xtensa')\n\nexport const targetArchs = /** @type {const} */ ([\n  defaultTargetArch,\n  ...riscTargetArchs,\n])\n\n/** @typedef {(typeof targetArchs)[number]} DecodeTarget */\n\n/** @typedef {(typeof riscTargetArchs)[number]} RiscvTargetArch */\n\n/**\n * @param {unknown} arg\n * @returns {arg is RiscvTargetArch}\n */\nexport function isRiscvTargetArch(arg) {\n  return (\n    typeof arg === 'string' &&\n    riscTargetArchs.includes(/** @type {RiscvTargetArch} */ (arg))\n  )\n}\n\nconst buildMcu = 'build.mcu'\n\n/**\n * @param {FindTargetArchParams} params\n * @returns {DecodeTarget}\n */\nexport function findTargetArch({ buildProperties }) {\n  const mcu = buildProperties[buildMcu]\n  if (isRiscvTargetArch(mcu)) {\n    return mcu\n  }\n  return defaultTargetArch\n}\n\nconst esp32 = 'esp32'\nconst esp8266 = 'esp8266'\nconst supportedArchitectures = new Set([esp32, esp8266])\n\nconst defaultTarch = 'xtensa'\nconst defaultTarget = 'lx106'\n\nconst buildTarch = 'build.tarch'\nconst buildTarget = 'build.target'\n\n/**\n * @typedef {Object} ResolveToolPathParams\n * @property {import('fqbn').FQBN} fqbn\n * @property {Record<string, string>} buildProperties\n */\n\n/**\n * @param {ResolveToolPathParams} params\n * @returns {Promise<string>}\n */\nexport async function resolveToolPath({ fqbn, buildProperties }) {\n  const { arch } = fqbn\n  if (!supportedArchitectures.has(arch)) {\n    throw new Error(`Unsupported board architecture: '${fqbn}'`)\n  }\n  let tarch = defaultTarch\n  let target = defaultTarget\n  if (arch === esp32) {\n    tarch = buildProperties[buildTarch] ?? defaultTarch\n    target = buildProperties[buildTarget] ?? defaultTarget\n  }\n\n  const toolchain = `${tarch}-${target}-elf`\n  const gdbTool = `${tarch}-esp-elf-gdb`\n  const gdb = appendDotExeOnWindows(`${toolchain}-gdb`)\n\n  /** @type {(key: string) => Promise<string | undefined>} */\n  async function find(key) {\n    const value = buildProperties[key]\n    if (value) {\n      const toolPath = path.join(value, 'bin', gdb)\n      try {\n        await fs.access(toolPath)\n        return toolPath\n      } catch {}\n    }\n    return undefined\n  }\n\n  // `runtime.tools.*` won't work for ESP32 installed from Git. See https://github.com/arduino/arduino-cli/issues/2197#issuecomment-1572921357.\n  // `runtime.tools.*` ESP8266 requires this. Hence, the fallback here.\n  const gdbToolPath = `tools.${gdbTool}.path`\n  const toolChainGCCPath = `tools.${toolchain}-gcc.path`\n  const toolPaths = await Promise.all([\n    find(`runtime.${gdbToolPath}`),\n    find(`runtime.${toolChainGCCPath}`),\n    find(gdbToolPath),\n    find(toolChainGCCPath),\n  ])\n  const toolPath = toolPaths.find((p) => p)\n  if (!toolPath) {\n    throw new Error(`Could not find GDB tool for '${fqbn}'`)\n  }\n  return toolPath\n}\n\n/**\n * @typedef {Object} ExecBoardDetailsParams\n * @property {import('fqbn').FQBN} fqbn\n * @property {string} arduinoCliPath\n * @property {string} [arduinoCliConfigPath]\n * @property {string} [additionalUrls]\n * @property {AbortSignal} [signal]\n */\n\n/** @param {ExecBoardDetailsParams} params */\nasync function execBoardDetails({\n  fqbn,\n  arduinoCliPath,\n  arduinoCliConfigPath,\n  additionalUrls,\n  signal,\n}) {\n  const args = ['board', 'details', '-b', fqbn.toString(), '--format', 'json']\n  if (arduinoCliConfigPath) {\n    args.push('--config-file', arduinoCliConfigPath)\n  }\n  if (additionalUrls) {\n    args.push('--additional-urls', additionalUrls)\n  }\n  return exec(arduinoCliPath, args, { signal })\n}\n\n/** @param {string[]} properties */\nfunction parseBuildProperties(properties) {\n  return properties.reduce((acc, curr) => {\n    const entry = parseProperty(curr)\n    if (entry) {\n      const [key, value] = entry\n      acc[key] = value\n    }\n    return acc\n  }, /** @type {Record<string, string>} */ ({}))\n}\n\nconst propertySep = '='\n/** @param {string} property */\nfunction parseProperty(property) {\n  const segments = property.split(propertySep)\n  if (segments.length < 2) {\n    console.warn(`Could not parse build property: ${property}.`)\n    return undefined\n  }\n  const [key, ...rest] = segments\n  if (!key) {\n    console.warn(`Could not determine property key from raw: ${property}.`)\n    return undefined\n  }\n  const value = rest.join(propertySep)\n  return [key, value]\n}\n\n/** (non-API) */\nexport const __tests = /** @type {const} */ ({\n  parseProperty,\n})\n","// @ts-check\n\nimport { execFile } from 'node:child_process'\n\n/**\n * @param {string} file\n * @param {string[]} [args=[]] Default is `[]`\n * @param {import('node:child_process').ExecFileOptions} [options={}] Default is\n *   `{}`\n * @returns {Promise<{ stdout: string; stderr: string }>}\n */\nexport async function exec(file, args = [], options = {}) {\n  return new Promise((resolve, reject) => {\n    execFile(file, args, options, (error, stdout, stderr) => {\n      if (error) {\n        reject(error)\n      } else {\n        resolve({\n          stdout: stdout.toString(),\n          stderr: stderr.toString(),\n        })\n      }\n    })\n  })\n}\n","// The module cache\nvar __webpack_module_cache__ = {};\n\n// The require function\nfunction __webpack_require__(moduleId) {\n\t// Check if module is in cache\n\tvar cachedModule = __webpack_module_cache__[moduleId];\n\tif (cachedModule !== undefined) {\n\t\treturn cachedModule.exports;\n\t}\n\t// Create a new module (and put it into the cache)\n\tvar module = __webpack_module_cache__[moduleId] = {\n\t\t// no module.id needed\n\t\t// no module.loaded needed\n\t\texports: {}\n\t};\n\n\t// Execute the module function\n\t__webpack_modules__[moduleId](module, module.exports, __webpack_require__);\n\n\t// Return the exports of the module\n\treturn module.exports;\n}\n\n","// define getter functions for harmony exports\n__webpack_require__.d = (exports, definition) => {\n\tfor(var key in definition) {\n\t\tif(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {\n\t\t\tObject.defineProperty(exports, key, { enumerable: true, get: definition[key] });\n\t\t}\n\t}\n};","__webpack_require__.o = (obj, prop) => (Object.prototype.hasOwnProperty.call(obj, prop))","// define __esModule on exports\n__webpack_require__.r = (exports) => {\n\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n\t}\n\tObject.defineProperty(exports, '__esModule', { value: true });\n};","// @ts-check\n\n/** @typedef {import('../tool.js').RiscvTargetArch} RiscvTargetArch */\n\nconst defaultRiscvTarget = /** @type {const} */ ('esp32c3')\n\nconst gdbRegsInfoRiscvIlp32 = /** @type {const} */ ([\n  'X0',\n  'RA',\n  'SP',\n  'GP',\n  'TP',\n  'T0',\n  'T1',\n  'T2',\n  'S0/FP',\n  'S1',\n  'A0',\n  'A1',\n  'A2',\n  'A3',\n  'A4',\n  'A5',\n  'A6',\n  'A7',\n  'S2',\n  'S3',\n  'S4',\n  'S5',\n  'S6',\n  'S7',\n  'S8',\n  'S9',\n  'S10',\n  'S11',\n  'T3',\n  'T4',\n  'T5',\n  'T6',\n  'MEPC',\n])\n\n/**\n * @typedef {Object} RegisterDump\n * @property {number} coreId\n * @property {Record<string, number>} regs\n */\n\n/**\n * @typedef {Object} StackDump\n * @property {number} baseAddr\n * @property {number[]} data\n */\n\n/**\n * @typedef {Object} ParsePanicOutputParams\n * @property {string} input\n * @property {RiscvTargetArch} [target]\n */\n\n/**\n * @typedef {Object} ParsePanicOutputResult\n * @property {RegisterDump[]} regDumps\n * @property {StackDump[]} stackDump\n * @property {number} programCounter\n * @property {number} [faultCode]\n * @property {number} [faultAddr]\n */\n\n/** @type {Record<RiscvTargetArch, gdbRegsInfoRiscvIlp32>} */\nconst gdbRegsInfo = {\n  esp32c2: gdbRegsInfoRiscvIlp32,\n  esp32c3: gdbRegsInfoRiscvIlp32,\n  esp32c6: gdbRegsInfoRiscvIlp32,\n  esp32h2: gdbRegsInfoRiscvIlp32,\n  esp32h4: gdbRegsInfoRiscvIlp32,\n  esp32p4: gdbRegsInfoRiscvIlp32,\n}\n\n/**\n * @template {RiscvTargetArch} T\n * @param {T} type\n */\nfunction createRegNameValidator(type) {\n  const regsInfo = gdbRegsInfo[type]\n  if (!regsInfo) {\n    throw new Error(`Unsupported target: ${type}`)\n  }\n  /** @type {(regName: unknown) => regName is gdbRegsInfoRiscvIlp32} */\n  return (regName) =>\n    regsInfo.includes(\n      /** @type {(typeof gdbRegsInfoRiscvIlp32)[number]} */ (regName)\n    )\n}\n\n/**\n * @param {ParsePanicOutputParams} params\n * @returns {ParsePanicOutputResult}\n */\nfunction parse({ input, target }) {\n  const lines = input.split(/\\r?\\n|\\r/)\n  /** @type {RegisterDump[]} */\n  const regDumps = []\n  /** @type {StackDump[]} */\n  const stackDump = []\n  /** @type {RegisterDump | undefined} */\n  let currentRegDump\n  let inStackMemory = false\n  /** @type {number | undefined} */\n  let faultCode\n  /** @type {number | undefined} */\n  let faultAddr\n  let programCounter = 0\n\n  const regNameValidator = createRegNameValidator(target ?? defaultRiscvTarget)\n\n  lines.forEach((line) => {\n    if (line.startsWith('Core')) {\n      const match = line.match(/^Core\\s+(\\d+)\\s+register dump:/)\n      if (match) {\n        currentRegDump = {\n          coreId: parseInt(match[1], 10),\n          regs: {},\n        }\n        regDumps.push(currentRegDump)\n      }\n    } else if (currentRegDump && !inStackMemory) {\n      const regMatches = line.matchAll(/([A-Z_0-9/]+)\\s*:\\s*(0x[0-9a-fA-F]+)/g)\n      for (const match of regMatches) {\n        const regName = match[1]\n        const regAddr = parseInt(match[2], 16)\n        if (regAddr && regNameValidator(regName)) {\n          currentRegDump.regs[regName] = regAddr\n          if (regName === 'MEPC') {\n            programCounter = regAddr\n          }\n        } else if (regName === 'MCAUSE') {\n          faultCode = regAddr\n        } else if (regName === 'MTVAL') {\n          faultAddr = regAddr\n        }\n      }\n      if (line.trim() === 'Stack memory:') {\n        inStackMemory = true\n      }\n    } else if (inStackMemory) {\n      const match = line.match(/^([0-9a-fA-F]+):\\s*((?:0x[0-9a-fA-F]+\\s*)+)/)\n      if (match) {\n        const baseAddr = parseInt(match[1], 16)\n        const data = match[2]\n          .trim()\n          .split(/\\s+/)\n          .map((hex) => parseInt(hex, 16))\n        stackDump.push({ baseAddr, data })\n      }\n    }\n  })\n\n  return { regDumps, stackDump, faultCode, faultAddr, programCounter }\n}\n\n/**\n * @typedef {Object} GetStackAddrAndDataParams\n * @property {StackDump[]} stackDump\n */\n\n/**\n * @param {GetStackAddrAndDataParams} params\n * @returns {{ stackBaseAddr: number; stackData: Buffer }}\n */\nfunction getStackAddrAndData({ stackDump }) {\n  let stackBaseAddr = 0\n  let baseAddr = 0\n  let bytesInLine = 0\n  let stackData = Buffer.alloc(0)\n\n  stackDump.forEach((line) => {\n    const prevBaseAddr = baseAddr\n    baseAddr = line.baseAddr\n    if (stackBaseAddr === 0) {\n      stackBaseAddr = baseAddr\n    } else if (baseAddr !== prevBaseAddr + bytesInLine) {\n      throw new Error('Invalid base address')\n    }\n\n    const lineData = Buffer.concat(\n      line.data.map((word) => {\n        const buf = Buffer.alloc(4)\n        buf.writeUInt32LE(word >>> 0)\n        return buf\n      })\n    )\n    bytesInLine = lineData.length\n    stackData = Buffer.concat([stackData, lineData])\n  })\n\n  return { stackBaseAddr, stackData }\n}\n\n/**\n * @param {{ input: string; target?: RiscvTargetArch }} params\n * @returns {import('./decode.js').PanicInfoWithStackData}\n */\nexport function parseRiscvPanicOutput({ input, target }) {\n  const resolvedTarget = target ?? defaultRiscvTarget\n  const { regDumps, stackDump, programCounter, faultAddr, faultCode } = parse({\n    input,\n    target: resolvedTarget,\n  })\n  if (regDumps.length === 0) {\n    throw new Error('No register dumps found')\n  }\n  if (regDumps.length > 1) {\n    throw new Error('Handling of multi-core register dumps not implemented')\n  }\n\n  const { coreId, regs } = regDumps[0]\n  const { stackBaseAddr, stackData } = getStackAddrAndData({ stackDump })\n\n  return {\n    coreId,\n    programCounter,\n    faultAddr,\n    faultCode,\n    regs,\n    stackBaseAddr,\n    stackData,\n    target: resolvedTarget,\n  }\n}\n","// @ts-check\n\nimport { EventEmitter } from 'node:events'\n\nimport { AbortError } from '../abort.js'\nimport { parseRiscvPanicOutput } from '../decode/riscvPanicParse.js'\nimport {\n  parseESP32PanicOutput,\n  parseESP8266PanicOutput,\n} from '../decode/xtensaPanicParse.js'\nimport { CrashFramer } from './framer.js'\nimport { LineDecoder } from './lineDecoder.js'\n\n/** @typedef {import('./types.js').CapturerEvent} CapturerEvent */\n/** @typedef {import('./types.js').CapturerLightweight} CapturerLightweight */\n/** @typedef {import('./types.js').CapturerOptions} CapturerOptions */\n/** @typedef {import('./types.js').ResolvedCapturerOptions} ResolvedCapturerOptions */\n/** @typedef {import('./types.js').CapturerEventName} CapturerEventName */\n/** @typedef {import('./types.js').CapturerListener} CapturerListener */\n/** @typedef {import('./types.js').CapturerEvaluateOptions} CapturerEvaluateOptions */\n/** @typedef {import('./types.js').FramedCrashBlock} FramedCrashBlock */\n/** @typedef {import('./types.js').CapturerEvaluated} CapturerEvaluated */\n/** @typedef {import('./types.js').CapturerRawState} CapturerRawState */\n/** @typedef {import('./types.js').CapturerEvaluateContext} CapturerEvaluateContext */\n\nconst defaultOptions = /** @type {const} */ ({\n  quietPeriodMs: 200,\n  dedupWindowMs: 5000,\n  maxEvents: 100,\n  maxRawBytes: 128 * 1024,\n  maxRawLines: 2000,\n})\n\nexport class Capturer {\n  _eventBus = new EventEmitter()\n  _lineDecoder = new LineDecoder()\n  /** @type {CrashFramer} */\n  _framer\n  /** @type {ResolvedCapturerOptions} */\n  _options\n  /** @type {CapturerEvent[]} */\n  _events = []\n  /** @type {Map<string, CapturerEvent>} */\n  _eventsById = new Map()\n  /** @type {Map<string, string>} */\n  _signatureIndex = new Map()\n  /** @type {Map<string, Promise<CapturerEvaluated>>} */\n  _inFlightEvaluations = new Map()\n  /** @type {Uint8Array[]} */\n  _rawBytes = []\n  _rawByteLength = 0\n  /** @type {string[]} */\n  _rawLines = []\n  _nextId = 1\n\n  /** @param {CapturerOptions} [options] */\n  constructor(options = {}) {\n    this._options = resolveOptions(options)\n    this._framer = new CrashFramer({\n      quietPeriodMs: this._options.quietPeriodMs,\n    })\n  }\n\n  /**\n   * @param {Uint8Array} chunk\n   * @returns {void}\n   */\n  push(chunk) {\n    if (!(chunk instanceof Uint8Array)) {\n      throw new TypeError('Expected a Uint8Array monitor chunk')\n    }\n    this._rememberRawBytes(chunk)\n    const lines = this._lineDecoder.push(chunk)\n    this._processLines(lines)\n  }\n\n  /** @returns {void} */\n  flush() {\n    this._processLines(this._lineDecoder.flush())\n    this._finalizeBlocks(this._framer.flush(this._options.now()))\n  }\n\n  /** @returns {CapturerEvent[]} */\n  getEvents() {\n    return structuredClone(this._events)\n  }\n\n  /** @returns {CapturerRawState} */\n  getRawState() {\n    return {\n      bytes: this._rawBytes.map((chunk) => chunk.slice()),\n      byteLength: this._rawByteLength,\n      lines: [...this._rawLines],\n    }\n  }\n\n  /**\n   * @param {CapturerEventName} eventName\n   * @param {CapturerListener} listener\n   * @returns {() => void}\n   */\n  on(eventName, listener) {\n    this._eventBus.on(eventName, listener)\n    return () => {\n      this._eventBus.off(eventName, listener)\n    }\n  }\n\n  /**\n   * @param {string} eventId\n   * @param {CapturerEvaluateOptions} [options]\n   * @returns {Promise<CapturerEvaluated>}\n   */\n  async evaluate(eventId, options = {}) {\n    const event = this._eventsById.get(eventId)\n    if (!event) {\n      throw new Error(`Unknown event id: ${eventId}`)\n    }\n    if (event.evaluated) {\n      return event.evaluated\n    }\n    const existingJob = this._inFlightEvaluations.get(eventId)\n    if (existingJob) {\n      return existingJob\n    }\n\n    const job = this._evaluateEvent(event, options.signal)\n    this._inFlightEvaluations.set(eventId, job)\n\n    try {\n      return await job\n    } finally {\n      this._inFlightEvaluations.delete(eventId)\n    }\n  }\n\n  /**\n   * @param {CapturerEvent} event\n   * @param {AbortSignal | undefined} signal\n   * @returns {Promise<CapturerEvaluated>}\n   */\n  async _evaluateEvent(event, signal) {\n    if (signal?.aborted) {\n      throw new AbortError()\n    }\n\n    const evaluator = this._options.evaluateEvent\n\n    if (evaluator) {\n      const context = /** @type {CapturerEvaluateContext} */ ({\n        event: structuredClone(event),\n        signal,\n      })\n      const evaluated = await evaluator(context)\n\n      if (signal?.aborted) {\n        throw new AbortError()\n      }\n\n      event.evaluated = evaluated\n      this._emit('eventUpdated', event)\n      return evaluated\n    }\n\n    await Promise.resolve()\n\n    if (signal?.aborted) {\n      throw new AbortError()\n    }\n\n    const addrs = event.lightweight.backtraceAddrs.length\n      ? event.lightweight.backtraceAddrs\n      : toArray(event.lightweight.programCounter)\n    const evaluated = {\n      eventId: event.id,\n      evaluatedAt: this._options.now(),\n      status: /** @type {const} */ ('stub'),\n      frames: addrs.map((addr) => ({\n        addr,\n        location: toHex(addr),\n      })),\n    }\n\n    event.evaluated = evaluated\n    this._emit('eventUpdated', event)\n    return evaluated\n  }\n\n  /**\n   * @param {Uint8Array} chunk\n   * @returns {void}\n   */\n  _rememberRawBytes(chunk) {\n    this._rawBytes.push(chunk.slice())\n    this._rawByteLength += chunk.length\n\n    while (\n      this._rawByteLength > this._options.maxRawBytes &&\n      this._rawBytes[0]\n    ) {\n      const overflow = this._rawByteLength - this._options.maxRawBytes\n      const first = this._rawBytes[0]\n      if (overflow >= first.length) {\n        this._rawBytes.shift()\n        this._rawByteLength -= first.length\n        continue\n      }\n      this._rawBytes[0] = first.slice(overflow)\n      this._rawByteLength -= overflow\n    }\n  }\n\n  /**\n   * @param {string[]} lines\n   * @returns {void}\n   */\n  _processLines(lines) {\n    for (const line of lines) {\n      this._rememberRawLine(line)\n      const blocks = this._framer.pushLine(line, this._options.now())\n      this._finalizeBlocks(blocks)\n    }\n  }\n\n  /**\n   * @param {string} line\n   * @returns {void}\n   */\n  _rememberRawLine(line) {\n    this._rawLines.push(line)\n    while (this._rawLines.length > this._options.maxRawLines) {\n      this._rawLines.shift()\n    }\n  }\n\n  /**\n   * @param {FramedCrashBlock[]} blocks\n   * @returns {void}\n   */\n  _finalizeBlocks(blocks) {\n    for (const block of blocks) {\n      this._mergeEvent(block)\n    }\n  }\n\n  /**\n   * @param {FramedCrashBlock} block\n   * @returns {void}\n   */\n  _mergeEvent(block) {\n    const rawText = block.lines.join('\\n')\n    const kind = detectKind(block.lines)\n    const lightweight = parseLightweight(rawText, kind, block.reasonLine)\n    const signature = createSignature(kind, lightweight.reasonLine, lightweight)\n    const candidate = {\n      kind,\n      lines: [...block.lines],\n      rawText,\n      firstSeenAt: block.startedAt,\n      lastSeenAt: block.lastAt,\n      lightweight,\n      signature,\n    }\n\n    const exact = this._findRecentBySignature(candidate)\n    if (exact) {\n      this._mergeIntoExisting(\n        exact,\n        candidate,\n        shouldPreferCandidate(exact, candidate)\n      )\n      return\n    }\n\n    const byContainment = this._findRecentContainmentMatch(candidate)\n    if (byContainment) {\n      this._mergeIntoExisting(\n        byContainment,\n        candidate,\n        shouldPreferCandidate(byContainment, candidate)\n      )\n      return\n    }\n\n    const byFingerprint = this._findRecentFingerprintMatch(candidate)\n    if (byFingerprint) {\n      this._mergeIntoExisting(\n        byFingerprint,\n        candidate,\n        shouldPreferCandidate(byFingerprint, candidate)\n      )\n      return\n    }\n\n    const next = /** @type {CapturerEvent} */ ({\n      id: `event-${String(this._nextId).padStart(6, '0')}`,\n      signature,\n      kind,\n      lines: [...block.lines],\n      rawText,\n      firstSeenAt: block.startedAt,\n      lastSeenAt: block.lastAt,\n      count: 1,\n      lightweight,\n      fastFrames: undefined,\n      evaluated: undefined,\n    })\n    this._nextId++\n\n    this._events.push(next)\n    this._eventsById.set(next.id, next)\n    this._signatureIndex.set(next.signature, next.id)\n    this._trimEvents()\n    this._emit('eventDetected', next)\n  }\n\n  /**\n   * @param {{\n   *   signature: string\n   *   lastSeenAt: number\n   * }} candidate\n   * @returns {CapturerEvent | undefined}\n   */\n  _findRecentBySignature(candidate) {\n    const existingId = this._signatureIndex.get(candidate.signature)\n    const existing = existingId ? this._eventsById.get(existingId) : undefined\n    if (!existing) {\n      return undefined\n    }\n    if (!this._isWithinDedupWindow(existing, candidate.lastSeenAt)) {\n      return undefined\n    }\n    return existing\n  }\n\n  /**\n   * @param {{\n   *   kind: import('./types.js').CapturerEventKind\n   *   rawText: string\n   *   lastSeenAt: number\n   *   lightweight: CapturerLightweight\n   * }} candidate\n   * @returns {CapturerEvent | undefined}\n   */\n  _findRecentContainmentMatch(candidate) {\n    for (let i = this._events.length - 1; i >= 0; i--) {\n      const existing = this._events[i]\n      if (!this._isWithinDedupWindow(existing, candidate.lastSeenAt)) {\n        continue\n      }\n      if (!isLikelySameCrash(existing, candidate)) {\n        continue\n      }\n      const existingContains = containsNormalizedText(\n        existing.rawText,\n        candidate.rawText\n      )\n      const candidateContains = containsNormalizedText(\n        candidate.rawText,\n        existing.rawText\n      )\n      if (existingContains || candidateContains) {\n        return existing\n      }\n    }\n    return undefined\n  }\n\n  /**\n   * @param {{\n   *   kind: import('./types.js').CapturerEventKind\n   *   lightweight: CapturerLightweight\n   *   lastSeenAt: number\n   * }} candidate\n   * @returns {CapturerEvent | undefined}\n   */\n  _findRecentFingerprintMatch(candidate) {\n    const candidateFingerprint = createFingerprint(\n      candidate.kind,\n      candidate.lightweight\n    )\n    if (!candidateFingerprint) {\n      return undefined\n    }\n\n    for (let i = this._events.length - 1; i >= 0; i--) {\n      const existing = this._events[i]\n      if (!this._isWithinDedupWindow(existing, candidate.lastSeenAt)) {\n        continue\n      }\n      if (\n        createFingerprint(existing.kind, existing.lightweight) ===\n        candidateFingerprint\n      ) {\n        return existing\n      }\n    }\n    return undefined\n  }\n\n  /**\n   * @param {CapturerEvent} existing\n   * @param {{\n   *   lines: string[]\n   *   rawText: string\n   *   lightweight: CapturerLightweight\n   *   signature: string\n   *   lastSeenAt: number\n   * }} candidate\n   * @param {boolean} preferCandidate\n   * @returns {void}\n   */\n  _mergeIntoExisting(existing, candidate, preferCandidate) {\n    existing.count += 1\n    existing.lastSeenAt = Math.max(existing.lastSeenAt, candidate.lastSeenAt)\n\n    if (preferCandidate) {\n      existing.lines = [...candidate.lines]\n      existing.rawText = candidate.rawText\n      existing.lightweight = candidate.lightweight\n      this._reindexSignature(existing, candidate.signature)\n    }\n\n    this._emit('eventUpdated', existing)\n  }\n\n  /**\n   * @param {CapturerEvent} existing\n   * @param {string} signature\n   * @returns {void}\n   */\n  _reindexSignature(existing, signature) {\n    if (existing.signature === signature) {\n      this._signatureIndex.set(signature, existing.id)\n      return\n    }\n\n    const currentOwner = this._signatureIndex.get(existing.signature)\n    if (currentOwner === existing.id) {\n      this._signatureIndex.delete(existing.signature)\n    }\n    existing.signature = signature\n    this._signatureIndex.set(signature, existing.id)\n  }\n\n  /**\n   * @param {CapturerEvent} event\n   * @param {number} atMs\n   * @returns {boolean}\n   */\n  _isWithinDedupWindow(event, atMs) {\n    return atMs - event.lastSeenAt <= this._options.dedupWindowMs\n  }\n\n  /** @returns {void} */\n  _trimEvents() {\n    while (this._events.length > this._options.maxEvents) {\n      const removed = this._events.shift()\n      if (!removed) {\n        break\n      }\n      this._eventsById.delete(removed.id)\n      if (this._signatureIndex.get(removed.signature) === removed.id) {\n        this._signatureIndex.delete(removed.signature)\n      }\n    }\n  }\n\n  /**\n   * @param {CapturerEventName} eventName\n   * @param {CapturerEvent} event\n   * @returns {void}\n   */\n  _emit(eventName, event) {\n    this._eventBus.emit(eventName, structuredClone(event))\n  }\n}\n\n/**\n * @param {CapturerOptions} [options]\n * @returns {Capturer}\n */\nexport function createCapturer(options) {\n  return new Capturer(options)\n}\n\n/**\n * @param {CapturerOptions} options\n * @returns {ResolvedCapturerOptions}\n */\nfunction resolveOptions(options) {\n  return {\n    quietPeriodMs: options.quietPeriodMs ?? defaultOptions.quietPeriodMs,\n    dedupWindowMs: options.dedupWindowMs ?? defaultOptions.dedupWindowMs,\n    maxEvents: options.maxEvents ?? defaultOptions.maxEvents,\n    maxRawBytes: options.maxRawBytes ?? defaultOptions.maxRawBytes,\n    maxRawLines: options.maxRawLines ?? defaultOptions.maxRawLines,\n    now: options.now ?? Date.now,\n    evaluateEvent: options.evaluateEvent,\n  }\n}\n\n/**\n * @param {string[]} lines\n * @returns {import('./types.js').CapturerEventKind}\n */\nfunction detectKind(lines) {\n  const riscvHints = [/MCAUSE/, /\\bMEPC\\b/, /Stack memory:/, /MHARTID/]\n  if (lines.some((line) => riscvHints.some((hint) => hint.test(line)))) {\n    return 'riscv'\n  }\n  const xtensaHints = [\n    /Backtrace:/,\n    /EXCCAUSE/,\n    /EXCVADDR/,\n    /Guru Meditation Error:/,\n  ]\n  if (lines.some((line) => xtensaHints.some((hint) => hint.test(line)))) {\n    return 'xtensa'\n  }\n  return 'unknown'\n}\n\n/**\n * @param {string} rawText\n * @param {import('./types.js').CapturerEventKind} kind\n * @param {string | undefined} reasonLine\n * @returns {CapturerLightweight}\n */\nfunction parseLightweight(rawText, kind, reasonLine) {\n  try {\n    if (kind === 'riscv') {\n      const parsed = parseRiscvPanicOutput({ input: rawText })\n      return {\n        reasonLine: reasonLine?.trim(),\n        programCounter: parsed.programCounter,\n        faultCode: parsed.faultCode,\n        faultAddr: parsed.faultAddr,\n        regs: parsed.regs,\n        backtraceAddrs: toArray(parsed.programCounter),\n      }\n    }\n\n    if (kind === 'xtensa') {\n      let parsed = parseESP32PanicOutput(rawText)\n      if (\n        Object.keys(parsed.regs).length === 0 &&\n        parsed.backtraceAddrs.length === 0 &&\n        !parsed.programCounter\n      ) {\n        parsed = parseESP8266PanicOutput(rawText)\n      }\n      return {\n        reasonLine: reasonLine?.trim(),\n        programCounter: parsed.programCounter,\n        faultCode: parsed.faultCode,\n        faultAddr: parsed.faultAddr,\n        regs: parsed.regs,\n        backtraceAddrs: /** @type {number[]} */ (\n          parsed.backtraceAddrs.filter((addr) => Number.isFinite(addr))\n        ),\n      }\n    }\n  } catch {\n    // Keep capturer best-effort even when parsing fails.\n  }\n\n  return {\n    reasonLine: reasonLine?.trim(),\n    programCounter: undefined,\n    faultCode: undefined,\n    faultAddr: undefined,\n    regs: {},\n    backtraceAddrs: [],\n  }\n}\n\n/**\n * @param {import('./types.js').CapturerEventKind} kind\n * @param {string | undefined} reasonLine\n * @param {CapturerLightweight} lightweight\n * @returns {string}\n */\nfunction createSignature(kind, reasonLine, lightweight) {\n  const normalizedReason = normalizeReason(reasonLine)\n  const addrs = lightweight.backtraceAddrs.slice(0, 5)\n  if (addrs.length === 0 && lightweight.programCounter !== undefined) {\n    addrs.push(lightweight.programCounter)\n  }\n  const pcs = addrs.map((addr) => toHex(addr)).join(',')\n  const faultCode = lightweight.faultCode\n  return `${kind}|${normalizedReason || 'unknown'}|fc:${faultCode ?? 'na'}|${pcs || 'nopc'}`\n}\n\n/**\n * @param {string | undefined} line\n * @returns {string}\n */\nfunction normalizeReason(line) {\n  const text = String(line ?? '').replace(/\\r/g, '')\n  const guruStart = text.toLowerCase().indexOf('guru meditation error:')\n  const scoped = guruStart >= 0 ? text.slice(guruStart) : text\n  return scoped\n    .toLowerCase()\n    .replace(/0x[0-9a-f]+/gi, '0x')\n    .replace(/\\s+/g, ' ')\n    .trim()\n}\n\n/**\n * @param {CapturerEvent\n *   | {\n *       rawText: string\n *       lightweight: CapturerLightweight\n *     }} existing\n * @param {{\n *   rawText: string\n *   lightweight: CapturerLightweight\n * }} candidate\n * @returns {boolean}\n */\nfunction shouldPreferCandidate(existing, candidate) {\n  const existingScore = computeCompleteness(\n    existing.rawText,\n    existing.lightweight\n  )\n  const candidateScore = computeCompleteness(\n    candidate.rawText,\n    candidate.lightweight\n  )\n  if (candidateScore > existingScore) {\n    return true\n  }\n  if (candidateScore < existingScore) {\n    return false\n  }\n  return candidate.rawText.length > existing.rawText.length\n}\n\n/**\n * @param {string} rawText\n * @param {CapturerLightweight} lightweight\n * @returns {number}\n */\nfunction computeCompleteness(rawText, lightweight) {\n  let score = 0\n  if (normalizeReason(lightweight.reasonLine)) {\n    score += 1\n  }\n  if (lightweight.faultCode !== undefined) {\n    score += 1\n  }\n  if (lightweight.programCounter !== undefined) {\n    score += 2\n  }\n  score += Math.min(lightweight.backtraceAddrs.length, 5) * 2\n  if (Object.keys(lightweight.regs).length > 0) {\n    score += 1\n  }\n  if (/Backtrace:|Stack memory:/i.test(rawText)) {\n    score += 2\n  }\n  if (/Rebooting\\.\\.\\./i.test(rawText)) {\n    score += 1\n  }\n  return score\n}\n\n/**\n * @param {import('./types.js').CapturerEventKind} kind\n * @param {CapturerLightweight} lightweight\n * @returns {string}\n */\nfunction createFingerprint(kind, lightweight) {\n  const reason = normalizeReason(lightweight.reasonLine)\n  const pc = getPrimaryAddr(lightweight)\n  if (!reason && lightweight.faultCode === undefined && pc === undefined) {\n    return ''\n  }\n  return `${kind}|${reason || 'unknown'}|fc:${lightweight.faultCode ?? 'na'}|pc:${pc !== undefined ? toHex(pc) : 'na'}`\n}\n\n/**\n * @param {string} container\n * @param {string} candidate\n * @returns {boolean}\n */\nfunction containsNormalizedText(container, candidate) {\n  const containerNormalized = normalizeTextForContainment(container)\n  const candidateNormalized = normalizeTextForContainment(candidate)\n  if (!containerNormalized || !candidateNormalized) {\n    return false\n  }\n  return (\n    containerNormalized === candidateNormalized ||\n    containerNormalized.includes(candidateNormalized)\n  )\n}\n\n/**\n * @param {string} input\n * @returns {string}\n */\nfunction normalizeTextForContainment(input) {\n  return input\n    .replace(/\\r\\n?/g, '\\n')\n    .split('\\n')\n    .map((line) => line.trim())\n    .filter((line) => line.length > 0)\n    .join('\\n')\n}\n\n/**\n * @param {CapturerEvent\n *   | {\n *       kind: import('./types.js').CapturerEventKind\n *       rawText: string\n *       lightweight: CapturerLightweight\n *     }} existing\n * @param {{\n *   kind: import('./types.js').CapturerEventKind\n *   rawText: string\n *   lightweight: CapturerLightweight\n * }} candidate\n * @returns {boolean}\n */\nfunction isLikelySameCrash(existing, candidate) {\n  if (existing.kind !== candidate.kind) {\n    return false\n  }\n\n  const existingReason = normalizeReason(existing.lightweight.reasonLine)\n  const candidateReason = normalizeReason(candidate.lightweight.reasonLine)\n  if (existingReason && candidateReason) {\n    return existingReason === candidateReason\n  }\n\n  const existingPc = getPrimaryAddr(existing.lightweight)\n  const candidatePc = getPrimaryAddr(candidate.lightweight)\n  if (existingPc !== undefined && candidatePc !== undefined) {\n    return existingPc === candidatePc\n  }\n\n  if (\n    existing.lightweight.faultCode !== undefined &&\n    candidate.lightweight.faultCode !== undefined\n  ) {\n    return existing.lightweight.faultCode === candidate.lightweight.faultCode\n  }\n\n  return containsNormalizedText(existing.rawText, candidate.rawText)\n}\n\n/**\n * @param {CapturerLightweight} lightweight\n * @returns {number | undefined}\n */\nfunction getPrimaryAddr(lightweight) {\n  return lightweight.backtraceAddrs[0] ?? lightweight.programCounter\n}\n\n/**\n * @param {number} value\n * @returns {string}\n */\nfunction toHex(value) {\n  return `0x${(value >>> 0).toString(16)}`\n}\n\n/**\n * @param {number | undefined} value\n * @returns {number[]}\n */\nfunction toArray(value) {\n  return value === undefined ? [] : [value]\n}\n","// src/index.ts\nvar f = {\n  reset: [0, 0],\n  bold: [1, 22, \"\\x1B[22m\\x1B[1m\"],\n  dim: [2, 22, \"\\x1B[22m\\x1B[2m\"],\n  italic: [3, 23],\n  underline: [4, 24],\n  inverse: [7, 27],\n  hidden: [8, 28],\n  strikethrough: [9, 29],\n  black: [30, 39],\n  red: [31, 39],\n  green: [32, 39],\n  yellow: [33, 39],\n  blue: [34, 39],\n  magenta: [35, 39],\n  cyan: [36, 39],\n  white: [37, 39],\n  gray: [90, 39],\n  bgBlack: [40, 49],\n  bgRed: [41, 49],\n  bgGreen: [42, 49],\n  bgYellow: [43, 49],\n  bgBlue: [44, 49],\n  bgMagenta: [45, 49],\n  bgCyan: [46, 49],\n  bgWhite: [47, 49],\n  blackBright: [90, 39],\n  redBright: [91, 39],\n  greenBright: [92, 39],\n  yellowBright: [93, 39],\n  blueBright: [94, 39],\n  magentaBright: [95, 39],\n  cyanBright: [96, 39],\n  whiteBright: [97, 39],\n  bgBlackBright: [100, 49],\n  bgRedBright: [101, 49],\n  bgGreenBright: [102, 49],\n  bgYellowBright: [103, 49],\n  bgBlueBright: [104, 49],\n  bgMagentaBright: [105, 49],\n  bgCyanBright: [106, 49],\n  bgWhiteBright: [107, 49]\n}, h = Object.entries(f);\nfunction a(n) {\n  return String(n);\n}\na.open = \"\";\na.close = \"\";\nvar B = /* @__PURE__ */ h.reduce(\n  (n, [e]) => (n[e] = a, n),\n  { isColorSupported: !1 }\n);\nfunction m() {\n  return { ...B };\n}\nfunction C(n = !1) {\n  let e = typeof process != \"undefined\" ? process : void 0, i = (e == null ? void 0 : e.env) || {}, g = (e == null ? void 0 : e.argv) || [];\n  return !(\"NO_COLOR\" in i || g.includes(\"--no-color\")) && (\"FORCE_COLOR\" in i || g.includes(\"--color\") || (e == null ? void 0 : e.platform) === \"win32\" || n && i.TERM !== \"dumb\" || \"CI\" in i) || typeof window != \"undefined\" && !!window.chrome;\n}\nfunction p(n = !1) {\n  let e = C(n), i = (r, t, c, o) => {\n    let l = \"\", s = 0;\n    do\n      l += r.substring(s, o) + c, s = o + t.length, o = r.indexOf(t, s);\n    while (~o);\n    return l + r.substring(s);\n  }, g = (r, t, c = r) => {\n    let o = (l) => {\n      let s = String(l), b = s.indexOf(t, r.length);\n      return ~b ? r + i(s, t, c, b) + t : r + s + t;\n    };\n    return o.open = r, o.close = t, o;\n  }, u = {\n    isColorSupported: e\n  }, d = (r) => `\\x1B[${r}m`;\n  for (let [r, t] of h)\n    u[r] = e ? g(\n      d(t[0]),\n      d(t[1]),\n      t[2]\n    ) : a;\n  return u;\n}\n\nexport {\n  m as a,\n  C as b,\n  p as c\n};\n","import {\n  a as e,\n  b as t,\n  c as o\n} from \"./chunk-BVHSVHOK.js\";\n\n// src/node.ts\nimport { isatty as s } from \"tty\";\nvar r = process.env.FORCE_TTY !== void 0 || s(1);\nfunction n() {\n  return t(r);\n}\nfunction a() {\n  return o(r);\n}\nvar u = o(r);\nexport {\n  a as createColors,\n  u as default,\n  e as getDefaultColors,\n  n as isSupported\n};\n","// @ts-check\n\nimport colors, { createColors as tinyrainbowCreateColors } from 'tinyrainbow'\n\nimport { isParsedGDBLine } from './decode.js'\n\n/** @typedef {import('./coredump.js').CoredumpDecodeResult} CoredumpDecodeResult */\n/** @typedef {import('./coredump.js').ThreadDecodeResult} ThreadDecodeResult */\n\nconst defaultOptions = {\n  forceColor: false,\n  lineSeparator: '\\r\\n',\n}\n\n/**\n * @typedef {Object} StringifyOptions\n * @property {'force' | 'disable'} [color]\n * @property {string} [lineSeparator='\\n'] Default is `'\\n'`\n */\n\n/**\n * @param {CoredumpDecodeResult} result\n * @param {ColorizeFn} colorizeFn\n */\nfunction stringifyCoredumpDecodeResult(result, colorizeFn) {\n  const lines = [...stringifyThreadsInfo(result, colorizeFn), '']\n\n  for (let i = 0; i < result.length; i++) {\n    const thread = result[i]\n    lines.push(\n      formatThreadHeader(thread),\n      ...stringifyThreadDecodeResult(thread, colorizeFn)\n    )\n    if (i < result.length - 1) {\n      lines.push('')\n    }\n  }\n\n  return lines\n}\n\n/**\n * @param {import('./decode.js').DecodeResult | CoredumpDecodeResult} result\n * @param {StringifyOptions} [options]\n */\nexport function stringifyDecodeResult(result, options = defaultOptions) {\n  options = { ...defaultOptions, ...options }\n  const { colorizeFn, resetColor } = createColorFn(options)\n\n  try {\n    const lines = Array.isArray(result)\n      ? stringifyCoredumpDecodeResult(result, colorizeFn)\n      : stringifySingleDecodeResult(result, colorizeFn)\n    return lines.join(options.lineSeparator)\n  } finally {\n    resetColor()\n  }\n}\n\n/**\n * @typedef {'red' | 'green' | 'blue'} Color\n *\n * @callback ColorizeFn\n * @param {string} text\n * @param {Color} [color]\n * @returns {string}\n */\n\n/**\n * @param {Pick<StringifyOptions, 'color'>} options\n * @returns {{ colorizeFn: ColorizeFn; resetColor: () => void }}\n */\nfunction createColorFn(options) {\n  const create =\n    (\n      /** @type {(arg: string) => string} */ red,\n      /** @type {(arg: string) => string} */ green,\n      /** @type {(arg: string) => string} */ blue\n    ) =>\n    (/** @type {string} */ text, /** @type {Color | undefined} */ color) => {\n      switch (color) {\n        case 'red':\n          return red(text)\n        case 'green':\n          return green(text)\n        case 'blue':\n          return blue(text)\n        default:\n          return text\n      }\n    }\n  /** @type {() => void} */\n  let resetColor = () => {\n    /* NOOP */\n  }\n\n  if (options.color === 'disable') {\n    return {\n      colorizeFn: (text) => text,\n      resetColor,\n    }\n  }\n\n  if (options.color === 'force') {\n    if (!process.env.FORCE_COLOR) {\n      process.env.FORCE_COLOR = '1'\n      resetColor = () => {\n        delete process.env.FORCE_COLOR\n      }\n    }\n\n    const { red, green, blue } = tinyrainbowCreateColors()\n    const colorizeFn = create(red, green, blue)\n    return {\n      colorizeFn,\n      resetColor,\n    }\n  }\n\n  const { red, green, blue } = colors\n  const colorizeFn = create(red, green, blue)\n  return {\n    colorizeFn,\n    resetColor,\n  }\n}\n\n/**\n * @param {import('./decode.js').DecodeResult} result\n * @param {ColorizeFn} colorizeFn\n */\nfunction stringifySingleDecodeResult(result, colorizeFn) {\n  const lines = []\n  if (typeof result.faultInfo?.faultCode === 'number') {\n    let faultCodeLine = `${result.faultInfo.coreId}`\n    if (result.faultInfo.faultMessage) {\n      faultCodeLine += ` | ${result.faultInfo.faultMessage}`\n    }\n    faultCodeLine += ` | ${result.faultInfo.faultCode}`\n    lines.push(colorizeFn(faultCodeLine, 'red'))\n  }\n\n  const pc = result.faultInfo?.programCounter.location\n  if (pc) {\n    if (lines.length) {\n      lines.push('')\n    }\n    lines.push(\n      `${colorizeFn('PC -> ', 'red')}${stringifyAddrLocation(pc, colorizeFn)}`\n    )\n  }\n\n  const faultAddr = result.faultInfo?.faultAddr?.location\n  if (faultAddr) {\n    lines.push(\n      `${colorizeFn('Fault -> ', 'red')}${stringifyAddrLocation(\n        faultAddr,\n        colorizeFn\n      )}`\n    )\n  }\n\n  if (result.stacktraceLines.length && lines.length) {\n    lines.push('')\n  }\n\n  for (const line of result.stacktraceLines) {\n    lines.push(stringifyAddrLocation(line, colorizeFn))\n  }\n\n  if (result.allocInfo) {\n    if (lines.length) {\n      lines.push('')\n    }\n    lines.push(\n      `${colorizeFn(\n        `Memory allocation of ${result.allocInfo.allocSize} bytes failed`,\n        'red'\n      )}${colorizeFn(' at ')}${stringifyAddrLocation(\n        result.allocInfo.allocAddr,\n        colorizeFn\n      )}`\n    )\n  }\n\n  return lines\n}\n\n/**\n * @param {CoredumpDecodeResult} result\n * @param {ColorizeFn} colorizeFn\n */\nfunction stringifyThreadsInfo(result, colorizeFn) {\n  const lines = []\n  lines.push('==================== THREADS INFO ====================')\n  lines.push('  ID  Target ID            Frame')\n\n  for (const thread of result) {\n    const mark = thread.current ? '*' : ' '\n    const tid = thread.threadId.toString().padStart(2)\n    const tcb = thread.TCB.toString().padEnd(12)\n    const top = thread.result.stacktraceLines?.[0]\n    lines.push(\n      ` ${mark}${tid}  process ${tcb} ${stringifyAddrLocation(top, colorizeFn)}`\n    )\n  }\n  return lines\n}\n\n/** @param {ThreadDecodeResult} thread */\nfunction formatThreadHeader(thread) {\n  return `==================== THREAD ${\n    thread.threadId\n  } (TCB: 0x${(+thread.TCB).toString(16)}) ====================`\n}\n\n/**\n * @param {ThreadDecodeResult} result\n * @param {ColorizeFn} colorizeFn\n */\nfunction stringifyThreadDecodeResult(result, colorizeFn) {\n  return result.result.stacktraceLines.map((line) =>\n    stringifyAddrLocation(line, colorizeFn)\n  )\n}\n\n/**\n * @typedef {Object} StringifyAddrLocationOptions\n * @property {(text: string, color?: 'green' | 'blue') => string} color\n */\n\n/**\n * @param {import('./decode.js').AddrLocation} location\n * @param {ColorizeFn} colorizeFn\n */\nfunction stringifyAddrLocation(location, colorizeFn) {\n  if (typeof location === 'string') {\n    return colorizeFn(location)\n  }\n  if (!isParsedGDBLine(location)) {\n    const regAddr = colorizeFn(location.regAddr, 'green')\n    const suffix = colorizeFn(`: ${location.lineNumber}`)\n    return `${regAddr}${suffix}`\n  }\n\n  const args =\n    location.args\n      ?.map((arg) => `${arg.name}${arg.value ? `=${arg.value}` : ''}`)\n      .join(', ') ?? ''\n\n  const signature = `${location.method} (${args})`\n\n  return `${colorizeFn(location.regAddr, 'green')}${colorizeFn(\n    ': '\n  )}${colorizeFn(signature, 'blue')}${colorizeFn(\n    ` at ${location.file}:${location.lineNumber}`\n  )}`\n}\n"],"names":["module","exports","require","AbortError","Error","constructor","super","this","name","code","neverSignal","AbortController","signal","startPatterns","reasonPatterns","CrashFramer","_quietPeriodMs","_active","options","quietPeriodMs","pushLine","line","atMs","finalized","_finalizeIfQuiet","isStartLine","_finalize","lines","startedAt","lastAt","reasonLine","undefined","push","some","pattern","test","isReasonLine","trim","flush","length","LineDecoder","_decoder","TextDecoder","_buffer","chunk","decode","stream","_drain","isFinal","start","i","ch","charCodeAt","slice","envDebugEnabled","process","env","TRBR_DEBUG","createRegAddrLogger","debug","writer","console","log","args","isParsedOrGdbLine","entry","Boolean","isGDBLine","isParsedGDBLine","parseLines","stdout","split","map","filter","patterns","entries","match","regAddr","method","file","lineNumber","normalizeParsedLine","fallbackMatch","parseLine","parsedMethod","sig","nameMatch","argsStr","arg","parts","value","s","parseMethodSignature","hasValidFile","hasValidLine","result","Object","assign","hasValidMethod","toHexString","number","toString","padStart","prompt","GDBSession","toolPath","elfPath","error","didExecuteFirstCommand","gdb","spawn","stdio","buffer","queue","current","on","_onData","stderr","err","reject","warn","idx","indexOf","output","resolve","_processQueue","item","shift","cmd","stdin","write","Promise","onData","includes","userError","exec","close","killed","end","kill","exitCode","once","async","addr2line","addrs","addresses","dedupedAddrs","Set","addr","addrNumber","has","add","Array","from","values","buildAddr2LineAddrs","results","Map","session","hex","parsedLines","location","find","set","addrOrLine","get","clientSeq","preview","text","limit","GdbMiClient","gdbPath","cp","id","prefix","createLogger","join","commandQueue","addEventListener","abortErr","forEach","executor","stdoutBuffer","sendCommand","command","Date","now","elapsed","drainHandshake","off","removeEventListener","onAbort","extractMiListContent","str","key","keyPattern","depth","c","substring","splitMiListItems","listContent","items","inQuotes","escape","char","Math","max","unescapeMiString","next","parseMiTuple","tupleContent","field","rawValue","startsWith","endsWith","parseMiResultRecord","raw","content","parseMiTupleList","tupleKey","tuples","trimmed","tupleBody","allowInfoFallback","TRBR_GLOBALS_ALLOW_INFO_VARIABLES","miErrorPattern","miUnsupportedPattern","createGlobalsLogger","replace","parseVariableLine","addrMatch","address","sanitized","lastSpace","lastIndexOf","rawName","type","pointerPrefix","arrayMatch","toGlobalVar","tuple","variable","scope","tryMiSymbolList","client","flag","resolveGlobalSymbols","params","timeoutMs","TRBR_GLOBALS_TIMEOUT_MS","parsed","Number","parseInt","isFinite","getGlobalsTimeoutMs","controller","timedOut","timeoutId","setTimeout","abort","aborted","allowInfo","coredumpMode","shouldAllowInfoFallback","globalVars","staticVars","miUnsupported","combined","reason","consoleText","vars","parseInfoVariables","extractMiConsoleText","deduped","existing","dedupeGlobals","listGlobalSymbols","clearTimeout","parseRegisters","regsRaw","miMatch","inner","regex","m","matchAll","parseBacktrace","obj","pair","val","decodeCoredump","input","tryRepair","inputPath","createCoredumpLogger","globals","threadsRaw","currentThreadMatch","currentThreadId","threadsContent","threadEntries","objs","objStart","objStr","threadIds","threadTcbs","fromEntries","tcb","tid","regNameMatch","regNames","regNameMap","parsedRegs","regsAsNamed","num","keys","programCounter","btOut","argsOut","argsListMatch","frameArgs","part","frameStr","rawMatch","levelMatch","level","argsMatchInner","argsContent","argRegex","stacktraceLines","frame","index","func","threadId","TCB","faultInfo","coreId","faultCode","regs","fs","fallback","expectedMagic","Buffer","offset","e_phoff","readUInt32LE","e_phentsize","readUInt16LE","e_phnum","elfTotalSize","entryOffset","elfBuffer","subarray","tmpDirPath","path","os","extractedElfPath","tryRawElfFallback","recursive","force","catch","createRiscvLogger","gdbRegsInfoRiscvIlp32","riscvDecoders","esp32c2","decodeRiscv","esp32c3","esp32c6","esp32h2","esp32h4","esp32p4","gdbRegsInfo","parsePanicOutput","target","regDumps","stackDump","faultAddr","currentRegDump","inStackMemory","regNameValidator","regsInfo","regName","createRegNameValidator","regMatches","baseAddr","data","parse","stackBaseAddr","stackData","bytesInLine","alloc","prevBaseAddr","lineData","concat","word","buf","writeUInt32LE","getStackAddrAndData","GdbServer","panicInfo","regList","server","net","abortHandler","listen","socket","pending","_consumePackets","packetStart","JSON","stringify","ignored","checksumMark","packet","_handleCommand","_respond","_respondRegs","size","v","_respondMem","res","reduce","sum","byte","response","regVal","regBytes","r","startAddr","stackAddrMin","stackLen","stackAddrMax","inStack","describeMiFailure","parseMiErrorMessage","normalized","summarizeMiOutput","shouldIncludeFrameVars","includeFrameVars","toFrameArg","toParsedFrame","fileRaw","fullname","isDefined","parseMiStackArgs","frameLevel","frames","stripMiList","parseMiLocals","toFrameVar","stripEntrySuffix","dedupeArgs","byName","order","baseName","fromEntry","filterArgLocals","locals","argNames","names","collectArgNames","local","shouldExpandVar","cleaned","normalizeType","isPrimitiveType","quoteMiArg","toVarChildEntry","displayName","exp","varObject","numChildren","numchild","isAccessSpecifier","expandVarObjectChildren","visited","maxDepth","children","listVarChildren","childVarObject","expanded","child","maxChildren","expandVariable","expression","createRaw","record","evaluated","evaluateExpression","expandLocals","exceptions","description","processPanicOutput","gdbServer","port","targetResult","framesRaw","rawArgs","parsedFrame","fetchStacktraceWithMi","targetArch","isRiscvTargetArch","inputType","faultAdd","all","exception","e","faultMessage","allocInfo","createDecodeResult","reserved","getAddr","addrLocation","parsedAddr","isNaN","isDecodeInputFileSource","isDecodeInputStreamSource","inputStream","Readable","parseESP8266PanicOutput","defaultTargetArch","decoders","logXtensa","createXtensaLogger","parseESP32PanicOutput","backtraceAddrs","decodedAddrs","addrLines","arches","isDecodeTarget","decodeInput","createDecodeLogger","isCoredumpModeParams","toDispose","coredumpInput","fd","createWriteStream","pipeline","allSettled","then","cleanupTasks","task","status","threadDecodeResult","fixDecodeResult","decoder","unsupportedTargetArch","texts","fixedResult","dispose","filteredResult","toLowerCase","filterFreeRTOSStackLines","fixWindowsPathInLocation","allocAddr","fixWindowsPaths","acc","currentLine","thisArray","prevLine","prevAddr","isAddr3x","isPrevAddr4x","isStackPointerLine","filterStackPointerLines","fixedFaultInfoResult","copy","fixFaultInfo","dedupedResult","previousLine","right","left","dedupeGDBLines","locationAware","fixWindowsPath","platform","createDecodeParams","isToolPathParams","buildProperties","isBuildPropertiesParams","resolveToolPath","findTargetArch","arduinoCliPath","isArduinoCliParams","resolveBuildProperties","fqbn","decodeParams","regLine","epcMatches","reg","toUpperCase","stackMatch","words","EPC1","coreIdMatch","regRegex","hexValue","matches","EXCCAUSE","EXCVADDR","PC","appendDotExeOnWindows","filename","findToolPath","arduinoCliConfigPath","additionalUrls","execFile","execBoardDetails","build_properties","curr","property","segments","rest","parseProperty","riscTargetArchs","mcu","esp32","supportedArchitectures","defaultTarch","defaultTarget","arch","tarch","toolchain","gdbTool","gdbToolPath","toolChainGCCPath","p","__webpack_module_cache__","__webpack_require__","moduleId","cachedModule","__webpack_modules__","d","definition","o","defineProperty","enumerable","prop","prototype","hasOwnProperty","call","Symbol","toStringTag","defaultRiscvTarget","parseRiscvPanicOutput","resolvedTarget","defaultOptions","Capturer","_eventBus","EventEmitter","_lineDecoder","_framer","_options","_events","_eventsById","_signatureIndex","_inFlightEvaluations","_rawBytes","_rawByteLength","_rawLines","_nextId","dedupWindowMs","maxEvents","maxRawBytes","maxRawLines","evaluateEvent","resolveOptions","Uint8Array","TypeError","_rememberRawBytes","_processLines","_finalizeBlocks","getEvents","structuredClone","getRawState","bytes","byteLength","eventName","listener","evaluate","eventId","event","existingJob","job","_evaluateEvent","delete","evaluator","context","_emit","lightweight","toArray","evaluatedAt","toHex","overflow","first","_rememberRawLine","blocks","block","_mergeEvent","rawText","kind","riscvHints","hint","xtensaHints","detectKind","parseLightweight","signature","normalizedReason","normalizeReason","pcs","createSignature","candidate","firstSeenAt","lastSeenAt","exact","_findRecentBySignature","_mergeIntoExisting","shouldPreferCandidate","byContainment","_findRecentContainmentMatch","byFingerprint","_findRecentFingerprintMatch","String","count","fastFrames","_trimEvents","existingId","_isWithinDedupWindow","isLikelySameCrash","existingContains","containsNormalizedText","candidateContains","candidateFingerprint","createFingerprint","preferCandidate","_reindexSignature","removed","emit","createCapturer","guruStart","existingScore","computeCompleteness","candidateScore","score","min","pc","getPrimaryAddr","container","containerNormalized","normalizeTextForContainment","candidateNormalized","existingReason","candidateReason","existingPc","candidatePc","h","reset","bold","dim","italic","underline","inverse","hidden","strikethrough","black","red","green","yellow","blue","magenta","cyan","white","gray","bgBlack","bgRed","bgGreen","bgYellow","bgBlue","bgMagenta","bgCyan","bgWhite","blackBright","redBright","greenBright","yellowBright","blueBright","magentaBright","cyanBright","whiteBright","bgBlackBright","bgRedBright","bgGreenBright","bgYellowBright","bgBlueBright","bgMagentaBright","bgCyanBright","bgWhiteBright","a","n","g","argv","TERM","window","chrome","C","t","l","b","open","u","isColorSupported","FORCE_TTY","forceColor","lineSeparator","stringifyDecodeResult","colorizeFn","resetColor","create","color","FORCE_COLOR","colors","createColorFn","isArray","stringifyThreadsInfo","thread","formatThreadHeader","stringifyThreadDecodeResult","stringifyCoredumpDecodeResult","faultCodeLine","stringifyAddrLocation","allocSize","stringifySingleDecodeResult","mark","padEnd","top"],"sourceRoot":""}