@coana-tech/cli 14.12.79 → 14.12.81

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,6 +1,4 @@
1
1
  import { createRequire } from 'module'; const require = createRequire(import.meta.url);
2
- const __dirname = import.meta.dirname
3
- const __filename = import.meta.filename
4
2
  var __create = Object.create;
5
3
  var __defProp = Object.defineProperty;
6
4
  var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
@@ -20911,12 +20909,10 @@ if (Number.parseInt(process.versions.node, 10) < 22) {
20911
20909
  next: { value: next, writable: true, configurable: true }
20912
20910
  });
20913
20911
  };
20914
- iteratorImpl2 = iteratorImpl;
20915
20912
  class It {
20916
20913
  [Symbol.iterator]() {
20917
20914
  return this;
20918
20915
  }
20919
- // Iterator.prototype.map
20920
20916
  map(fn) {
20921
20917
  const iterator = this;
20922
20918
  let index = 0;
@@ -20927,7 +20923,6 @@ if (Number.parseInt(process.versions.node, 10) < 22) {
20927
20923
  return { value: fn(result.value, index++), done: false };
20928
20924
  });
20929
20925
  }
20930
- // Iterator.prototype.filter
20931
20926
  filter(fn) {
20932
20927
  const iterator = this;
20933
20928
  let index = 0;
@@ -20941,7 +20936,6 @@ if (Number.parseInt(process.versions.node, 10) < 22) {
20941
20936
  }
20942
20937
  });
20943
20938
  }
20944
- // Iterator.prototype.take
20945
20939
  take(n12) {
20946
20940
  const iterator = this;
20947
20941
  let count = 0;
@@ -20952,7 +20946,6 @@ if (Number.parseInt(process.versions.node, 10) < 22) {
20952
20946
  return iterator.next();
20953
20947
  });
20954
20948
  }
20955
- // Iterator.prototype.drop
20956
20949
  drop(n12) {
20957
20950
  const iterator = this;
20958
20951
  let count = 0;
@@ -20966,7 +20959,6 @@ if (Number.parseInt(process.versions.node, 10) < 22) {
20966
20959
  return iterator.next();
20967
20960
  });
20968
20961
  }
20969
- // Iterator.prototype.toArray
20970
20962
  toArray() {
20971
20963
  const result = [];
20972
20964
  let next = this.next();
@@ -20976,13 +20968,11 @@ if (Number.parseInt(process.versions.node, 10) < 22) {
20976
20968
  }
20977
20969
  return result;
20978
20970
  }
20979
- // Iterator.prototype.forEach
20980
20971
  forEach(fn) {
20981
20972
  let index = 0;
20982
20973
  for (const value of this)
20983
20974
  fn(value, index++);
20984
20975
  }
20985
- // Iterator.prototype.some
20986
20976
  some(fn) {
20987
20977
  let index = 0;
20988
20978
  for (const value of this)
@@ -20990,7 +20980,6 @@ if (Number.parseInt(process.versions.node, 10) < 22) {
20990
20980
  return true;
20991
20981
  return false;
20992
20982
  }
20993
- // Iterator.prototype.every
20994
20983
  every(fn) {
20995
20984
  let index = 0;
20996
20985
  for (const value of this)
@@ -20998,14 +20987,12 @@ if (Number.parseInt(process.versions.node, 10) < 22) {
20998
20987
  return false;
20999
20988
  return true;
21000
20989
  }
21001
- // Iterator.prototype.find
21002
20990
  find(fn) {
21003
20991
  let index = 0;
21004
20992
  for (const value of this)
21005
20993
  if (fn(value, index++))
21006
20994
  return value;
21007
20995
  }
21008
- // Iterator.prototype.reduce
21009
20996
  reduce(fn, initialValue) {
21010
20997
  let accumulator = initialValue;
21011
20998
  let index = 0;
@@ -21020,7 +21007,6 @@ if (Number.parseInt(process.versions.node, 10) < 22) {
21020
21007
  throw new TypeError("Reduce of empty iterator with no initial value");
21021
21008
  return accumulator;
21022
21009
  }
21023
- // Iterator.prototype.flatMap
21024
21010
  flatMap(fn) {
21025
21011
  const iterator = this;
21026
21012
  let currentIterator;
@@ -21045,7 +21031,6 @@ if (Number.parseInt(process.versions.node, 10) < 22) {
21045
21031
  }
21046
21032
  });
21047
21033
  }
21048
- // Iterator.from
21049
21034
  static from(value) {
21050
21035
  if (value === void 0)
21051
21036
  throw new TypeError("Iterator.from requires a value");
@@ -21084,7 +21069,6 @@ if (Number.parseInt(process.versions.node, 10) < 22) {
21084
21069
  Object.setPrototypeOf(proto, It.prototype);
21085
21070
  }
21086
21071
  }
21087
- var iteratorImpl2;
21088
21072
 
21089
21073
  // ../../node_modules/.pnpm/commander@14.0.2/node_modules/commander/esm.mjs
21090
21074
  var import_index = __toESM(require_commander(), 1);
@@ -21277,7 +21261,7 @@ function n11(e5, t15) {
21277
21261
  }
21278
21262
  var r2 = (n12, { preserveConsecutiveUppercase: r3 = true } = {}) => t13(t14.test(n12) ? n12 : n12.toLowerCase()).map((e5, t15) => `${t15 === 0 ? e5[0].toLowerCase() : e5[0].toUpperCase()}${r3 ? e5.slice(1) : e5.slice(1).toLowerCase()}`).join(``);
21279
21263
 
21280
- // ../utils/src/asserts.ts
21264
+ // ../utils/dist/asserts.js
21281
21265
  import { format } from "node:util";
21282
21266
  function assertDefined(value, msg, ...params) {
21283
21267
  if (value === void 0 || value === null)
@@ -21285,7 +21269,7 @@ function assertDefined(value, msg, ...params) {
21285
21269
  return value;
21286
21270
  }
21287
21271
 
21288
- // ../utils/src/collections.ts
21272
+ // ../utils/dist/collections.js
21289
21273
  function getOrSet(m, k, v) {
21290
21274
  let r3 = m.get(k);
21291
21275
  if (r3 === void 0) {
@@ -21346,7 +21330,8 @@ var Queue = class {
21346
21330
  }
21347
21331
  pop() {
21348
21332
  if (this.items.length === 0) {
21349
- if (this.back.length === 0) throw new Error("Queue is empty");
21333
+ if (this.back.length === 0)
21334
+ throw new Error("Queue is empty");
21350
21335
  [this.items, this.back] = [this.back.reverse(), this.items];
21351
21336
  }
21352
21337
  return this.items.pop();
@@ -21362,31 +21347,25 @@ var Queue = class {
21362
21347
  }
21363
21348
  };
21364
21349
 
21365
- // ../utils/src/logger.ts
21350
+ // ../utils/dist/logger.js
21366
21351
  var import_winston = __toESM(require_winston(), 1);
21367
21352
  import { tmpdir } from "node:os";
21368
21353
  import { sep } from "node:path";
21369
21354
  var logger = (0, import_winston.createLogger)({
21370
21355
  level: "info",
21371
- format: import_winston.format.combine(
21372
- import_winston.format.splat(),
21373
- import_winston.format.timestamp({ format: "YYYY-MM-DD HH:mm:ss.SSS" }),
21374
- ...process.stdout.isTTY ? [import_winston.format.colorize()] : [],
21375
- // eslint-disable-next-line @typescript-eslint/no-base-to-string
21376
- import_winston.format.printf(({ level, message, label, timestamp }) => `${timestamp} ${label ?? "-"} ${level}: ${message}`)
21377
- ),
21356
+ format: import_winston.format.combine(import_winston.format.splat(), import_winston.format.timestamp({ format: "YYYY-MM-DD HH:mm:ss.SSS" }), ...process.stdout.isTTY ? [import_winston.format.colorize()] : [], import_winston.format.printf(({ level, message, label, timestamp }) => `${timestamp} ${label ?? "-"} ${level}: ${message}`)),
21378
21357
  transports: [new import_winston.default.transports.Console()]
21379
21358
  });
21380
21359
  function setLogLevel(level) {
21381
21360
  logger.level = level;
21382
21361
  }
21383
21362
 
21384
- // ../utils/src/numbers.ts
21363
+ // ../utils/dist/numbers.js
21385
21364
  function percent(part, total) {
21386
21365
  return `${Math.round(part / (total || 1) * 1e4) / 100}%`;
21387
21366
  }
21388
21367
 
21389
- // ../utils/src/source-locations.ts
21368
+ // ../utils/dist/source-locations.js
21390
21369
  function locationToString(location, { filename = true } = {}) {
21391
21370
  return `${filename ? `${location.filename}:` : ""}${location.start.line}:${location.start.column}:${location.end.line}:${location.end.column}`;
21392
21371
  }
@@ -21398,7 +21377,7 @@ function createDummyLocation(filepath) {
21398
21377
  };
21399
21378
  }
21400
21379
 
21401
- // ../utils/src/tree-sitter-ast-utils.ts
21380
+ // ../utils/dist/tree-sitter-ast-utils.js
21402
21381
  import assert2 from "node:assert";
21403
21382
  var PRINT_NODES = !!process.env["PRINT_NODES"];
21404
21383
  function visit(rootNode, astVisitor) {
@@ -21415,13 +21394,17 @@ function visit(rootNode, astVisitor) {
21415
21394
  const gen = visitor(cursor.currentNode);
21416
21395
  if (gen !== void 0) {
21417
21396
  visitChildren = false;
21418
- for (const child of gen) visitNode(child);
21397
+ for (const child of gen)
21398
+ visitNode(child);
21419
21399
  }
21420
21400
  }
21421
- if (visitChildren && cursor.gotoFirstChild()) continue;
21401
+ if (visitChildren && cursor.gotoFirstChild())
21402
+ continue;
21422
21403
  while (true) {
21423
- if (cursor.gotoNextSibling()) break;
21424
- if (!cursor.gotoParent()) return;
21404
+ if (cursor.gotoNextSibling())
21405
+ break;
21406
+ if (!cursor.gotoParent())
21407
+ return;
21425
21408
  }
21426
21409
  }
21427
21410
  }
@@ -21460,7 +21443,9 @@ function nodeEq(a, b) {
21460
21443
  var NodeMap = class {
21461
21444
  map = /* @__PURE__ */ new Map();
21462
21445
  constructor(iterable) {
21463
- if (iterable !== void 0) for (const [key, value] of iterable) this.set(key, value);
21446
+ if (iterable !== void 0)
21447
+ for (const [key, value] of iterable)
21448
+ this.set(key, value);
21464
21449
  }
21465
21450
  get size() {
21466
21451
  return this.map.size;
@@ -21515,16 +21500,19 @@ var FullNodeMap = class {
21515
21500
  return this.entries();
21516
21501
  }
21517
21502
  forEach(callbackfn, thisArg) {
21518
- for (const [key, value] of this) callbackfn.call(thisArg, value, key, this);
21503
+ for (const [key, value] of this)
21504
+ callbackfn.call(thisArg, value, key, this);
21519
21505
  }
21520
21506
  entries() {
21521
21507
  return this.map.values();
21522
21508
  }
21523
21509
  *keys() {
21524
- for (const [key] of this) yield key;
21510
+ for (const [key] of this)
21511
+ yield key;
21525
21512
  }
21526
21513
  *values() {
21527
- for (const [, value] of this) yield value;
21514
+ for (const [, value] of this)
21515
+ yield value;
21528
21516
  }
21529
21517
  };
21530
21518
  var NodeSet = class {
@@ -21553,25 +21541,30 @@ var NodeSet = class {
21553
21541
  [Symbol.toStringTag] = "NodeSet";
21554
21542
  };
21555
21543
 
21556
- // ../analysis-engine/src/infos.ts
21544
+ // ../analysis-engine/dist/infos.js
21557
21545
  import { join } from "node:path";
21558
21546
  var PackageInfo = class {
21559
- // map from path relative to the package root to module info
21560
- // readonly directDependencies = new Set<PackageInfo>(); // the direct dependencies of this package
21547
+ name;
21548
+ version;
21549
+ dir;
21550
+ isEntry;
21551
+ modules = /* @__PURE__ */ new Map();
21561
21552
  constructor(name, version, dir, isEntry) {
21562
21553
  this.name = name;
21563
21554
  this.version = version;
21564
21555
  this.dir = dir;
21565
21556
  this.isEntry = isEntry;
21566
21557
  }
21567
- modules = /* @__PURE__ */ new Map();
21568
21558
  toString() {
21569
21559
  return `${this.name}${this.version ? `@${this.version}` : ""}`;
21570
21560
  }
21571
21561
  };
21572
21562
  var ModuleInfo = class {
21573
- // top-level source location, dummy if not yet analyzed
21574
- // readonly hash: number;
21563
+ relativePath;
21564
+ packageInfo;
21565
+ isEntry;
21566
+ isIncluded;
21567
+ loc;
21575
21568
  constructor(relativePath, packageInfo, isEntry, isIncluded) {
21576
21569
  this.relativePath = relativePath;
21577
21570
  this.packageInfo = packageInfo;
@@ -21579,29 +21572,19 @@ var ModuleInfo = class {
21579
21572
  this.isIncluded = isIncluded;
21580
21573
  this.loc = createDummyLocation(this.getPath());
21581
21574
  }
21582
- // readonly functions = new Set<FunctionInfo>(); // functions directly inside this module
21583
- loc;
21584
21575
  toString() {
21585
21576
  return `${this.packageInfo}:${this.relativePath}`;
21586
21577
  }
21587
- /**
21588
- * Returns normalized file path of the representative file (different paths may refer to the same ModuleInfo).
21589
- */
21590
21578
  getPath() {
21591
21579
  return join(this.packageInfo.dir, this.relativePath);
21592
21580
  }
21593
- /**
21594
- * Returns the official name of this module, using the package name if the module is the main module,
21595
- * and otherwise stripping /index.js, .js and .mjs.
21596
- */
21597
- /*
21598
- getOfficialName(): string {
21599
- if (this.relativePath === this.packageInfo.main) return this.packageInfo.name;
21600
- return normalizeModuleName(`${this.packageInfo.name}/${this.relativePath}`);
21601
- }
21602
- */
21603
21581
  };
21604
21582
  var FunctionInfo = class {
21583
+ name;
21584
+ node;
21585
+ parent;
21586
+ moduleInfo;
21587
+ loc;
21605
21588
  constructor(name, node, parent, moduleInfo) {
21606
21589
  this.name = name;
21607
21590
  this.node = node;
@@ -21609,8 +21592,6 @@ var FunctionInfo = class {
21609
21592
  this.moduleInfo = moduleInfo;
21610
21593
  this.loc = getSourceLocation(node);
21611
21594
  }
21612
- // readonly functions = new Set<FunctionInfo>(); // functions directly inside this function
21613
- loc;
21614
21595
  get isEntry() {
21615
21596
  return this.moduleInfo.isEntry;
21616
21597
  }
@@ -21622,23 +21603,11 @@ var FunctionInfo = class {
21622
21603
  }
21623
21604
  };
21624
21605
 
21625
- // ../analysis-engine/src/call-graph.ts
21606
+ // ../analysis-engine/dist/call-graph.js
21626
21607
  var CallGraph = class {
21627
- /**
21628
- * Map that provides for each function/module the set of functions that may be called.
21629
- */
21630
21608
  functionToFunction = /* @__PURE__ */ new Map();
21631
- /**
21632
- * Map that provides for each call-site the set of functions that may be called.
21633
- */
21634
21609
  callToFunctionOrModule = new FullNodeMap();
21635
- /**
21636
- * Map that provides for each call-site the innermost function that contains it.
21637
- */
21638
21610
  callToContainingFunction = new NodeMap();
21639
- /**
21640
- * Adds an edge in the call graph (both function->function and call->function).
21641
- */
21642
21611
  addEdge(call, from, to) {
21643
21612
  const fs4 = mapGetSet(this.functionToFunction, from);
21644
21613
  fs4.add(to);
@@ -21654,12 +21623,9 @@ var CallGraph = class {
21654
21623
  return this.callToFunctionOrModule.entries().flatMap(([call, tos]) => {
21655
21624
  const from = assertDefined(this.callToContainingFunction.get(call));
21656
21625
  const loc = locationToString(from.loc);
21657
- return tos.keys().map(
21658
- (to) => `${loc} ${locationToString(getSourceLocation(call), { filename: false })} -> ${locationToString(to.loc)}`
21659
- );
21626
+ return tos.keys().map((to) => `${loc} ${locationToString(getSourceLocation(call), { filename: false })} -> ${locationToString(to.loc)}`);
21660
21627
  }).toArray();
21661
21628
  }
21662
- // Returns a parent map for all reachable functions starting from `initial`
21663
21629
  reachableFunctions(initial) {
21664
21630
  const stack = [...initial];
21665
21631
  const parent = new Map(stack.map((f) => [f, void 0]));
@@ -21676,7 +21642,8 @@ var CallGraph = class {
21676
21642
  serialize() {
21677
21643
  const targetIndex = /* @__PURE__ */ new Map();
21678
21644
  for (const f of [...this.functionToFunction.keys(), ...this.functionToFunction.values().flatMap(e3())]) {
21679
- if (targetIndex.has(f)) continue;
21645
+ if (targetIndex.has(f))
21646
+ continue;
21680
21647
  targetIndex.set(f, targetIndex.size);
21681
21648
  }
21682
21649
  const edgeIndex = /* @__PURE__ */ new Map();
@@ -21736,14 +21703,7 @@ function compareStaticWithDynamicCG(callGraph, moduleInfos, { targets, edges },
21736
21703
  staticLibReachable
21737
21704
  };
21738
21705
  }
21739
- function comparisonReport({
21740
- dynamicEdges,
21741
- dynamicReachable,
21742
- dynamicLibReachable,
21743
- staticEdges,
21744
- staticReachable,
21745
- staticLibReachable
21746
- }) {
21706
+ function comparisonReport({ dynamicEdges, dynamicReachable, dynamicLibReachable, staticEdges, staticReachable, staticLibReachable }) {
21747
21707
  const sse = new Set(staticEdges);
21748
21708
  const ssr = new Set(staticReachable);
21749
21709
  const sslr = new Set(staticLibReachable);
@@ -21764,13 +21724,13 @@ Extra: ${fmt(staticReachable.length - reachableMatches, staticReachable.length)}
21764
21724
  `;
21765
21725
  }
21766
21726
 
21767
- // ../ruby-analyzer/src/ruby-analyzer.ts
21727
+ // ../ruby-analyzer/dist/ruby-analyzer.js
21768
21728
  import assert9 from "node:assert";
21769
21729
  import { createReadStream } from "node:fs";
21770
21730
  import { readFile } from "node:fs/promises";
21771
21731
  import { basename as basename2, dirname as dirname3, resolve as resolve2 } from "node:path";
21772
21732
 
21773
- // ../utils/src/files.ts
21733
+ // ../utils/dist/files.js
21774
21734
  import { access, readdir, stat } from "node:fs/promises";
21775
21735
  import { resolve } from "node:path";
21776
21736
  async function findFiles(dir, predicate, recurse = e2(true)) {
@@ -21780,32 +21740,33 @@ async function findFiles(dir, predicate, recurse = e2(true)) {
21780
21740
  for (const entry of entries) {
21781
21741
  const fullPath = resolve(dir2, entry.name);
21782
21742
  const e5 = entry.isSymbolicLink() ? await stat(fullPath) : entry;
21783
- if (e5.isDirectory() && recurse(fullPath)) await aux(fullPath);
21784
- else if (e5.isFile() && await predicate(fullPath)) files.push(fullPath);
21743
+ if (e5.isDirectory() && recurse(fullPath))
21744
+ await aux(fullPath);
21745
+ else if (e5.isFile() && await predicate(fullPath))
21746
+ files.push(fullPath);
21785
21747
  }
21786
21748
  };
21787
21749
  await aux(dir);
21788
21750
  return files;
21789
21751
  }
21790
21752
 
21791
- // ../utils/src/timer.ts
21753
+ // ../utils/dist/timer.js
21792
21754
  var Timer = class {
21755
+ timeout;
21756
+ startTime;
21793
21757
  constructor(timeout) {
21794
21758
  this.timeout = timeout;
21795
21759
  this.reset();
21796
21760
  }
21797
- startTime;
21798
21761
  reset() {
21799
21762
  this.startTime = process.hrtime.bigint();
21800
21763
  }
21801
- /**
21802
- * Returns the elapsed time in nanoseconds since the timer was created.
21803
- */
21804
21764
  elapsed() {
21805
21765
  return process.hrtime.bigint() - this.startTime;
21806
21766
  }
21807
21767
  checkTimeout() {
21808
- if (this.timeout && this.elapsed() > BigInt(this.timeout) * 1000000000n) throw new TimeoutException();
21768
+ if (this.timeout && this.elapsed() > BigInt(this.timeout) * 1000000000n)
21769
+ throw new TimeoutException();
21809
21770
  }
21810
21771
  };
21811
21772
  var TimeoutException = class extends Error {
@@ -21817,12 +21778,14 @@ function nanoToMs(n12) {
21817
21778
  return `${n12 / 1000000n}ms`;
21818
21779
  }
21819
21780
 
21820
- // ../analysis-engine/src/abstract-constraintvar.ts
21781
+ // ../analysis-engine/dist/abstract-constraintvar.js
21821
21782
  var ConstraintVar = class {
21822
21783
  };
21823
21784
 
21824
- // ../ruby-analyzer/src/constraintvars.ts
21785
+ // ../ruby-analyzer/dist/constraintvars.js
21825
21786
  var NodeVar = class extends ConstraintVar {
21787
+ node;
21788
+ kind;
21826
21789
  constructor(node, kind) {
21827
21790
  super();
21828
21791
  this.node = node;
@@ -21833,6 +21796,8 @@ var NodeVar = class extends ConstraintVar {
21833
21796
  }
21834
21797
  };
21835
21798
  var MethodsVar = class extends ConstraintVar {
21799
+ obj;
21800
+ name;
21836
21801
  constructor(obj, name) {
21837
21802
  super();
21838
21803
  this.obj = obj;
@@ -21843,6 +21808,7 @@ var MethodsVar = class extends ConstraintVar {
21843
21808
  }
21844
21809
  };
21845
21810
  var AncestorsVar = class extends ConstraintVar {
21811
+ obj;
21846
21812
  constructor(obj) {
21847
21813
  super();
21848
21814
  this.obj = obj;
@@ -21852,6 +21818,7 @@ var AncestorsVar = class extends ConstraintVar {
21852
21818
  }
21853
21819
  };
21854
21820
  var ConstantVar = class extends ConstraintVar {
21821
+ constant;
21855
21822
  constructor(constant) {
21856
21823
  super();
21857
21824
  this.constant = constant;
@@ -21861,6 +21828,8 @@ var ConstantVar = class extends ConstraintVar {
21861
21828
  }
21862
21829
  };
21863
21830
  var ObjPropVar = class extends ConstraintVar {
21831
+ obj;
21832
+ prop;
21864
21833
  constructor(obj, prop) {
21865
21834
  super();
21866
21835
  this.obj = obj;
@@ -21871,7 +21840,7 @@ var ObjPropVar = class extends ConstraintVar {
21871
21840
  }
21872
21841
  };
21873
21842
 
21874
- // ../ruby-analyzer/src/types/ruby-node-types.ts
21843
+ // ../ruby-analyzer/dist/types/ruby-node-types.js
21875
21844
  function isAliasNode(node) {
21876
21845
  return node?.type === "alias";
21877
21846
  }
@@ -21990,10 +21959,12 @@ function isStringContentNode(node) {
21990
21959
  return node?.type === "string_content";
21991
21960
  }
21992
21961
 
21993
- // ../ruby-analyzer/src/ruby-ast-helpers.ts
21962
+ // ../ruby-analyzer/dist/ruby-ast-helpers.js
21994
21963
  function getStringContent(node) {
21995
- if (node.namedChildCount === 0) return "";
21996
- else if (node.namedChildCount === 1 && isStringContentNode(node.namedChildren[0])) return node.namedChildren[0].text;
21964
+ if (node.namedChildCount === 0)
21965
+ return "";
21966
+ else if (node.namedChildCount === 1 && isStringContentNode(node.namedChildren[0]))
21967
+ return node.namedChildren[0].text;
21997
21968
  const parts = [];
21998
21969
  for (const child of node.namedChildren)
21999
21970
  switch (child.type) {
@@ -22015,59 +21986,56 @@ function getStringContent(node) {
22015
21986
  }
22016
21987
  function getLastNodeInFunction(node) {
22017
21988
  const bodyNode = node.bodyNode;
22018
- if (!bodyNode) return;
21989
+ if (!bodyNode)
21990
+ return;
22019
21991
  const blockBodyNode = bodyNode.namedChildren.find((b) => b.type === "block_body");
22020
21992
  return (blockBodyNode ?? bodyNode).lastNamedChild;
22021
21993
  }
22022
21994
  function isCommandCall(node, bindings) {
22023
- if (bindings.has(node)) return false;
21995
+ if (bindings.has(node))
21996
+ return false;
22024
21997
  const { parent } = node;
22025
- if ((isMethodNode(parent) || isSingletonMethodNode(parent)) && parent.nameNode.id === node.id) return false;
22026
- if (isCallNode(parent) && parent.methodNode?.id === node.id) return false;
22027
- if (isAliasNode(parent) && parent.namedChildren.some((c) => c.id === node.id)) return false;
21998
+ if ((isMethodNode(parent) || isSingletonMethodNode(parent)) && parent.nameNode.id === node.id)
21999
+ return false;
22000
+ if (isCallNode(parent) && parent.methodNode?.id === node.id)
22001
+ return false;
22002
+ if (isAliasNode(parent) && parent.namedChildren.some((c) => c.id === node.id))
22003
+ return false;
22028
22004
  return true;
22029
22005
  }
22030
22006
 
22031
- // ../ruby-analyzer/src/constraintvar-producer.ts
22007
+ // ../ruby-analyzer/dist/constraintvar-producer.js
22032
22008
  var ConstraintVarProducer = class {
22033
- /**
22034
- * Map from AST node to canonical NodeVar object - This ensures that we only have one constraint variable per AST node.
22035
- */
22036
- canonicalNodeVars = t7(
22037
- ["normal", "callee", "return", "self", "default definee", "block param"],
22038
- () => new NodeMap()
22039
- );
22009
+ canonicalNodeVars = t7(["normal", "callee", "return", "self", "default definee", "block param"], () => new NodeMap());
22040
22010
  canonicalMethodsVars = /* @__PURE__ */ new Map();
22041
22011
  canonicalPropVars = /* @__PURE__ */ new Map();
22042
22012
  canonicalAncestorsVars = /* @__PURE__ */ new WeakMap();
22043
22013
  canonicalConstantVars = /* @__PURE__ */ new Map();
22044
- /**
22045
- * Map from constraint variable string hash to canonical ConstraintVar object.
22046
- */
22047
- // private readonly canonicalConstraintVars = new Map<string, RubyConstraintVar>();
22048
22014
  canonicalizeVar(v) {
22049
- if (v instanceof NodeVar) return getOrSet(this.canonicalNodeVars[v.kind], v.node, () => v);
22015
+ if (v instanceof NodeVar)
22016
+ return getOrSet(this.canonicalNodeVars[v.kind], v.node, () => v);
22050
22017
  else if (v instanceof MethodsVar) {
22051
22018
  const map = getOrSet(this.canonicalMethodsVars, v.name, () => /* @__PURE__ */ new WeakMap());
22052
22019
  return getOrSet(map, v.obj, () => v);
22053
22020
  } else if (v instanceof ConstantVar)
22054
22021
  return getOrSet(this.canonicalConstantVars, v.constant, () => v);
22055
- else if (v instanceof AncestorsVar) return getOrSet(this.canonicalAncestorsVars, v.obj, () => v);
22022
+ else if (v instanceof AncestorsVar)
22023
+ return getOrSet(this.canonicalAncestorsVars, v.obj, () => v);
22056
22024
  else if (v instanceof ObjPropVar) {
22057
22025
  const map = getOrSet(this.canonicalPropVars, v.prop, () => /* @__PURE__ */ new WeakMap());
22058
22026
  return getOrSet(map, v.obj, () => v);
22059
- } else v;
22027
+ } else
22028
+ v;
22060
22029
  throw new Error(`Unsupported constraint variable: ${v}`);
22061
22030
  }
22062
22031
  identVar(n12, bindings) {
22063
- if (isCommandCall(n12, bindings)) return this.nodeVar(n12);
22032
+ if (isCommandCall(n12, bindings))
22033
+ return this.nodeVar(n12);
22064
22034
  const def = bindings.get(n12);
22065
- if (!def) logger.error(`No definition found for identifier: ${n12.text}`);
22035
+ if (!def)
22036
+ logger.error(`No definition found for identifier: ${n12.text}`);
22066
22037
  return this.nodeVar(def);
22067
22038
  }
22068
- /**
22069
- * Finds the constraint variable representing the return values of the given function.
22070
- */
22071
22039
  returnVar(fun) {
22072
22040
  return this.canonicalizeVar(new NodeVar(fun, "return"));
22073
22041
  }
@@ -22100,18 +22068,18 @@ var ConstraintVarProducer = class {
22100
22068
  }
22101
22069
  };
22102
22070
 
22103
- // ../ruby-analyzer/src/natives/native-builder.ts
22071
+ // ../ruby-analyzer/dist/natives/native-builder.js
22104
22072
  import assert6 from "node:assert";
22105
22073
 
22106
- // ../ruby-analyzer/src/tokens.ts
22074
+ // ../ruby-analyzer/dist/tokens.js
22107
22075
  import assert3 from "node:assert";
22108
22076
 
22109
- // ../analysis-engine/src/abstract-token.ts
22077
+ // ../analysis-engine/dist/abstract-token.js
22110
22078
  var TokenInterface = class {
22111
22079
  hash;
22112
22080
  };
22113
22081
 
22114
- // ../utils/src/strings.ts
22082
+ // ../utils/dist/strings.js
22115
22083
  function strHash(s) {
22116
22084
  let h1 = 0;
22117
22085
  let h2 = 17656767856;
@@ -22127,7 +22095,7 @@ function strHash(s) {
22127
22095
  return 4294967296 * (2097151 & h2) + (h1 >>> 0);
22128
22096
  }
22129
22097
 
22130
- // ../ruby-analyzer/src/tokens.ts
22098
+ // ../ruby-analyzer/dist/tokens.js
22131
22099
  function makeConstant(name) {
22132
22100
  return name;
22133
22101
  }
@@ -22145,25 +22113,17 @@ var TokenFactory = class {
22145
22113
  canonicalMethodTokens = /* @__PURE__ */ new Map();
22146
22114
  canonicalizeToken(token) {
22147
22115
  if (token instanceof MethodToken) {
22148
- const map = getOrSet(
22149
- this.canonicalMethodTokens,
22150
- token.methodName,
22151
- () => /* @__PURE__ */ new WeakMap()
22152
- );
22116
+ const map = getOrSet(this.canonicalMethodTokens, token.methodName, () => /* @__PURE__ */ new WeakMap());
22153
22117
  return getOrSet(map, token.receiver, () => {
22154
22118
  token.hash = strHash(`Method;${token.receiver};${token.methodName}`);
22155
22119
  return token;
22156
22120
  });
22157
22121
  } else if (token instanceof ObjectToken) {
22158
- const { index, ...maps } = getOrSet(
22159
- this.canonicalObjectTokens,
22160
- token.klass,
22161
- () => ({
22162
- index: this.canonicalObjectTokens.size,
22163
- nodeInstances: new NodeMap(),
22164
- otherInstances: /* @__PURE__ */ new Map()
22165
- })
22166
- );
22122
+ const { index, ...maps } = getOrSet(this.canonicalObjectTokens, token.klass, () => ({
22123
+ index: this.canonicalObjectTokens.size,
22124
+ nodeInstances: new NodeMap(),
22125
+ otherInstances: /* @__PURE__ */ new Map()
22126
+ }));
22167
22127
  const site = token instanceof SingletonClassToken ? token.obj : token.allocSite;
22168
22128
  if (typeof site === "object" && "id" in site)
22169
22129
  return getOrSet(maps.nodeInstances, site, () => {
@@ -22181,14 +22141,16 @@ var TokenFactory = class {
22181
22141
  lambda: void 0
22182
22142
  }));
22183
22143
  const t15 = canon[token.kind] ??= token;
22184
- if (t15 === token) t15.hash = strHash(`${token.kind};${syntaxNodeToHashStr(token.fun)}`);
22144
+ if (t15 === token)
22145
+ t15.hash = strHash(`${token.kind};${syntaxNodeToHashStr(token.fun)}`);
22185
22146
  return t15;
22186
22147
  } else if (token instanceof NativeFunctionToken)
22187
22148
  return getOrSet(this.canonicalNativeFunctionTokens, token.native, () => {
22188
22149
  token.hash = strHash(token.native);
22189
22150
  return token;
22190
22151
  });
22191
- else token;
22152
+ else
22153
+ token;
22192
22154
  throw new Error(`Unknown token type: ${token}`);
22193
22155
  }
22194
22156
  createFunctionToken(fun, kind, scope, parameters = fun.parametersNode) {
@@ -22212,7 +22174,8 @@ var TokenFactory = class {
22212
22174
  };
22213
22175
  var ObjectToken = class extends TokenInterface {
22214
22176
  constructor(key) {
22215
- if (key !== tokenFactoryKey) throw new Error("ObjectToken must be created through TokenFactory");
22177
+ if (key !== tokenFactoryKey)
22178
+ throw new Error("ObjectToken must be created through TokenFactory");
22216
22179
  super();
22217
22180
  }
22218
22181
  isClassOrModuleToken() {
@@ -22223,6 +22186,7 @@ var ObjectToken = class extends TokenInterface {
22223
22186
  }
22224
22187
  };
22225
22188
  var ClassToken = class extends ObjectToken {
22189
+ allocSite;
22226
22190
  constructor(key, allocSite) {
22227
22191
  super(key);
22228
22192
  this.allocSite = allocSite;
@@ -22233,29 +22197,36 @@ var ClassToken = class extends ObjectToken {
22233
22197
  };
22234
22198
  var rubyClassToken = ClassToken.prototype.klass = new ClassToken(tokenFactoryKey, "::Class");
22235
22199
  var SingletonClassToken = class extends ObjectToken {
22200
+ obj;
22201
+ static {
22202
+ this.prototype.klass = rubyClassToken;
22203
+ }
22236
22204
  constructor(key, obj) {
22237
22205
  super(key);
22238
22206
  this.obj = obj;
22239
22207
  }
22240
- static {
22241
- this.prototype.klass = rubyClassToken;
22242
- }
22243
22208
  toString() {
22244
22209
  return `SingletonClass[${this.obj}]`;
22245
22210
  }
22246
22211
  };
22247
22212
  var InstanceToken = class extends ObjectToken {
22213
+ klass;
22214
+ allocSite;
22248
22215
  constructor(key, klass, allocSite) {
22249
22216
  super(key);
22250
22217
  this.klass = klass;
22251
22218
  this.allocSite = allocSite;
22252
22219
  }
22253
22220
  toString() {
22254
- if (this.allocSite === void 0) return `Instance[${this.klass}]`;
22221
+ if (this.allocSite === void 0)
22222
+ return `Instance[${this.klass}]`;
22255
22223
  return `Object[${typeof this.allocSite === "string" ? this.allocSite : `${this.allocSite.type}:${nodeLocationToString(this.allocSite)}`} < ${this.klass}]`;
22256
22224
  }
22257
22225
  };
22258
22226
  var MethodToken = class extends ObjectToken {
22227
+ klass;
22228
+ receiver;
22229
+ methodName;
22259
22230
  constructor(key, klass, receiver, methodName) {
22260
22231
  super(key);
22261
22232
  this.klass = klass;
@@ -22267,13 +22238,18 @@ var MethodToken = class extends ObjectToken {
22267
22238
  }
22268
22239
  };
22269
22240
  var FunctionToken = class extends TokenInterface {
22241
+ fun;
22242
+ parameters;
22243
+ kind;
22244
+ scope;
22270
22245
  constructor(key, fun, parameters, kind, scope) {
22271
22246
  super();
22272
22247
  this.fun = fun;
22273
22248
  this.parameters = parameters;
22274
22249
  this.kind = kind;
22275
22250
  this.scope = scope;
22276
- if (key !== tokenFactoryKey) throw new Error("FunctionToken must be created through TokenFactory");
22251
+ if (key !== tokenFactoryKey)
22252
+ throw new Error("FunctionToken must be created through TokenFactory");
22277
22253
  assert3(kind === "method" || isBlockNode(fun) || isDoBlockNode(fun));
22278
22254
  }
22279
22255
  toString() {
@@ -22281,31 +22257,33 @@ var FunctionToken = class extends TokenInterface {
22281
22257
  return `${t2(this.kind)}[${repr}]`;
22282
22258
  }
22283
22259
  toKind(kind, { tokenFactory }) {
22284
- if (this.kind === kind) return this;
22260
+ if (this.kind === kind)
22261
+ return this;
22285
22262
  return tokenFactory.createFunctionToken(this.fun, kind, this.scope, this.parameters);
22286
22263
  }
22287
22264
  };
22288
22265
  var NativeFunctionToken = class extends TokenInterface {
22289
- // TODO: maybe this belongs in the analysis-engine package
22266
+ native;
22267
+ invoke;
22290
22268
  constructor(key, native, invoke) {
22291
22269
  super();
22292
22270
  this.native = native;
22293
22271
  this.invoke = invoke;
22294
- if (key !== tokenFactoryKey) throw new Error("NativeObjectToken must be created through TokenFactory");
22272
+ if (key !== tokenFactoryKey)
22273
+ throw new Error("NativeObjectToken must be created through TokenFactory");
22295
22274
  }
22296
22275
  toString() {
22297
22276
  return `NativeFunction[${this.native}]`;
22298
22277
  }
22299
22278
  };
22300
22279
 
22301
- // ../utils/src/objects.ts
22280
+ // ../utils/dist/objects.js
22302
22281
  function maybeOmit(obj, key) {
22303
22282
  return key in obj ? n7(obj, [key]) : obj;
22304
22283
  }
22305
22284
 
22306
- // ../ruby-analyzer/src/natives/3rd-party/jwe.ts
22285
+ // ../ruby-analyzer/dist/natives/3rd-party/jwe.js
22307
22286
  var jwe_default = {
22308
- // TODO: Check whether these work for old versions
22309
22287
  "JWE::Enc": {
22310
22288
  fake: true,
22311
22289
  staticMethods: {
@@ -22327,20 +22305,22 @@ var jwe_default = {
22327
22305
  }
22328
22306
  };
22329
22307
 
22330
- // ../ruby-analyzer/src/natives/models/module.ts
22308
+ // ../ruby-analyzer/dist/natives/models/module.js
22331
22309
  import assert4 from "node:assert";
22332
22310
 
22333
- // ../utils/src/cache.ts
22311
+ // ../utils/dist/cache.js
22334
22312
  function cache(func, map = /* @__PURE__ */ new Map()) {
22335
22313
  return (key, ...rest) => {
22336
22314
  let value = map.get(key);
22337
- if (value === void 0) map.set(key, value = func(key, ...rest));
22315
+ if (value === void 0)
22316
+ map.set(key, value = func(key, ...rest));
22338
22317
  return value;
22339
22318
  };
22340
22319
  }
22341
22320
 
22342
- // ../ruby-analyzer/src/listeners.ts
22343
- var TokenListener = /* @__PURE__ */ ((TokenListener2) => {
22321
+ // ../ruby-analyzer/dist/listeners.js
22322
+ var TokenListener;
22323
+ (function(TokenListener2) {
22344
22324
  TokenListener2[TokenListener2["Call"] = 0] = "Call";
22345
22325
  TokenListener2[TokenListener2["Method"] = 1] = "Method";
22346
22326
  TokenListener2[TokenListener2["READ_BASE"] = 2] = "READ_BASE";
@@ -22369,10 +22349,9 @@ var TokenListener = /* @__PURE__ */ ((TokenListener2) => {
22369
22349
  TokenListener2[TokenListener2["NATIVE_BASIC_OBJECT_INSTANCE_EXEC_PROC"] = 25] = "NATIVE_BASIC_OBJECT_INSTANCE_EXEC_PROC";
22370
22350
  TokenListener2[TokenListener2["RAILS_INITIALIZABLE_INITIALIZER"] = 26] = "RAILS_INITIALIZABLE_INITIALIZER";
22371
22351
  TokenListener2[TokenListener2["RAILS_INITIALIZABLE_INITIALIZER_PROC"] = 27] = "RAILS_INITIALIZABLE_INITIALIZER_PROC";
22372
- return TokenListener2;
22373
- })(TokenListener || {});
22352
+ })(TokenListener || (TokenListener = {}));
22374
22353
 
22375
- // ../ruby-analyzer/src/natives/utils.ts
22354
+ // ../ruby-analyzer/dist/natives/utils.js
22376
22355
  function unsupported(klass, name) {
22377
22356
  return ({ cd, op }) => {
22378
22357
  op.a.warnUnsupported(cd.callNode, `Unsupported native method '${klass}#${name}'`);
@@ -22381,10 +22360,12 @@ function unsupported(klass, name) {
22381
22360
  };
22382
22361
  }
22383
22362
  function literalArg(op, cd, arg, method) {
22384
- if (!arg) op.a.warnUnsupported(cd.callNode, `${method} called with undefined (unsupported) argument`);
22363
+ if (!arg)
22364
+ op.a.warnUnsupported(cd.callNode, `${method} called with undefined (unsupported) argument`);
22385
22365
  else if (arg instanceof ConstraintVar || arg instanceof TokenInterface)
22386
22366
  op.a.warnUnsupported(cd.callNode, `${method} called with non-literal argument`);
22387
- else return arg;
22367
+ else
22368
+ return arg;
22388
22369
  }
22389
22370
  function invokeBlock(block, listener, defaultDefinee, p) {
22390
22371
  if (block) {
@@ -22392,25 +22373,24 @@ function invokeBlock(block, listener, defaultDefinee, p) {
22392
22373
  const key = { t: base, n: cd.callNode };
22393
22374
  op.addForAllTokensConstraint(block, listener, key, (t15) => {
22394
22375
  if (t15 instanceof ObjectToken) {
22395
- if (t15.klass !== op.state.globalNatives.Proc) return;
22396
- op.solver.addForAllTokensConstraint(
22397
- op.cvp.methodsVar(op.singletonClass(t15), "call"),
22398
- listener + 1,
22399
- key,
22400
- (ft) => {
22401
- if (ft instanceof FunctionToken) {
22402
- op.inclusionConstraint(defaultDefinee, op.cvp.defaultDefineeVar(ft.fun));
22403
- op.dispatchCall(ft.toKind("method", op), base, cd);
22404
- } else if (ft instanceof NativeFunctionToken) ft.invoke(p);
22405
- else ft;
22406
- }
22407
- );
22408
- } else t15;
22376
+ if (t15.klass !== op.state.globalNatives.Proc)
22377
+ return;
22378
+ op.solver.addForAllTokensConstraint(op.cvp.methodsVar(op.singletonClass(t15), "call"), listener + 1, key, (ft) => {
22379
+ if (ft instanceof FunctionToken) {
22380
+ op.inclusionConstraint(defaultDefinee, op.cvp.defaultDefineeVar(ft.fun));
22381
+ op.dispatchCall(ft.toKind("method", op), base, cd);
22382
+ } else if (ft instanceof NativeFunctionToken)
22383
+ ft.invoke(p);
22384
+ else
22385
+ ft;
22386
+ });
22387
+ } else
22388
+ t15;
22409
22389
  });
22410
22390
  }
22411
22391
  }
22412
22392
 
22413
- // ../ruby-analyzer/src/natives/models/module.ts
22393
+ // ../ruby-analyzer/dist/natives/models/module.js
22414
22394
  function include(kind, { base, op, cd }) {
22415
22395
  if (base instanceof SingletonClassToken) {
22416
22396
  op.a.warnUnsupported(cd.callNode, `Module#${kind} on a singleton class`);
@@ -22420,7 +22400,8 @@ function include(kind, { base, op, cd }) {
22420
22400
  logger.error(`Module#${kind} is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`);
22421
22401
  return;
22422
22402
  }
22423
- if (cd.arguments?.pSplat) op.a.warnUnsupported(cd.callNode, `Module#${kind} called with splat arguments`);
22403
+ if (cd.arguments?.pSplat)
22404
+ op.a.warnUnsupported(cd.callNode, `Module#${kind} called with splat arguments`);
22424
22405
  const ncd = {
22425
22406
  ...cd,
22426
22407
  arguments: { positional: [base] },
@@ -22428,46 +22409,44 @@ function include(kind, { base, op, cd }) {
22428
22409
  };
22429
22410
  for (const arg of cd.arguments?.positional ?? [])
22430
22411
  if (arg instanceof ConstraintVar || arg instanceof ObjectToken)
22431
- op.addForAllTokensConstraint(
22432
- arg,
22433
- 11 /* NATIVE_MODULE_INCLUDE */,
22434
- { t: base, s: kind, n: cd.callNode },
22435
- (t15) => {
22436
- if (t15 instanceof ObjectToken) {
22437
- if (t15.klass === op.state.globalNatives.Module) {
22438
- op.callMethod(t15, kind === "include" ? "append_features" : "prepend_features", ncd);
22439
- op.callMethod(t15, kind === "include" ? "included" : "prepended", ncd);
22440
- }
22441
- } else t15;
22442
- }
22443
- );
22444
- else arg;
22412
+ op.addForAllTokensConstraint(arg, TokenListener.NATIVE_MODULE_INCLUDE, { t: base, s: kind, n: cd.callNode }, (t15) => {
22413
+ if (t15 instanceof ObjectToken) {
22414
+ if (t15.klass === op.state.globalNatives.Module) {
22415
+ op.callMethod(t15, kind === "include" ? "append_features" : "prepend_features", ncd);
22416
+ op.callMethod(t15, kind === "include" ? "included" : "prepended", ncd);
22417
+ }
22418
+ } else
22419
+ t15;
22420
+ });
22421
+ else
22422
+ arg;
22445
22423
  }
22446
22424
  function appendFeatures({ base, op, cd }) {
22447
22425
  assert4.strictEqual(base.klass, op.state.globalNatives.Module);
22448
- if (cd.arguments?.pSplat) op.a.warnUnsupported(cd.callNode, "Module#append_features called with splat arguments");
22426
+ if (cd.arguments?.pSplat)
22427
+ op.a.warnUnsupported(cd.callNode, "Module#append_features called with splat arguments");
22449
22428
  const srcAv = op.cvp.ancestorsVar(base);
22450
22429
  for (const arg of cd.arguments?.positional ?? [])
22451
22430
  if (arg instanceof ConstraintVar || arg instanceof ObjectToken)
22452
- op.addForAllTokensConstraint(arg, 12 /* NATIVE_MODULE_APPEND_FEATURES */, { t: base }, (t15) => {
22431
+ op.addForAllTokensConstraint(arg, TokenListener.NATIVE_MODULE_APPEND_FEATURES, { t: base }, (t15) => {
22453
22432
  if (t15 instanceof ObjectToken) {
22454
22433
  if (t15 instanceof SingletonClassToken)
22455
22434
  op.a.warnUnsupported(cd.callNode, "Module#append_features called with a singleton class");
22456
- else if (t15.isClassOrModuleToken()) op.solver.addSubsetConstraint(srcAv, op.cvp.ancestorsVar(t15));
22435
+ else if (t15.isClassOrModuleToken())
22436
+ op.solver.addSubsetConstraint(srcAv, op.cvp.ancestorsVar(t15));
22457
22437
  else
22458
- throw new Error(
22459
- `Module#append_features is called with a non-Class or Module token ${t15} at ${nodeToString(cd.callNode)}`
22460
- );
22461
- } else t15;
22438
+ throw new Error(`Module#append_features is called with a non-Class or Module token ${t15} at ${nodeToString(cd.callNode)}`);
22439
+ } else
22440
+ t15;
22462
22441
  });
22463
- else arg;
22442
+ else
22443
+ arg;
22464
22444
  }
22465
22445
  function attrModel(name, { base, op, cd }) {
22466
22446
  if (!base.isClassLikeToken())
22467
- throw new Error(
22468
- `Module#attr_${name} is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`
22469
- );
22470
- if (cd.arguments?.pSplat) op.a.warnUnsupported(cd.callNode, `Module#attr_${name} called with splat arguments`);
22447
+ throw new Error(`Module#attr_${name} is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`);
22448
+ if (cd.arguments?.pSplat)
22449
+ op.a.warnUnsupported(cd.callNode, `Module#attr_${name} called with splat arguments`);
22471
22450
  for (const arg of cd.arguments?.positional ?? []) {
22472
22451
  const lArg = literalArg(op, cd, arg, `Module#attr_${name}`);
22473
22452
  if (lArg) {
@@ -22478,15 +22457,9 @@ function attrModel(name, { base, op, cd }) {
22478
22457
  }
22479
22458
  function attrModelImpl(op, name, base, attr) {
22480
22459
  if (name !== "writer")
22481
- op.solver.addTokenConstraint(
22482
- op.tokenFactory.createNativeFunctionToken(...attrReader(attr)),
22483
- op.cvp.methodsVar(base, attr)
22484
- );
22460
+ op.solver.addTokenConstraint(op.tokenFactory.createNativeFunctionToken(...attrReader(attr)), op.cvp.methodsVar(base, attr));
22485
22461
  if (name !== "reader")
22486
- op.solver.addTokenConstraint(
22487
- op.tokenFactory.createNativeFunctionToken(...attrWriter(attr)),
22488
- op.cvp.methodsVar(base, `${attr}=`)
22489
- );
22462
+ op.solver.addTokenConstraint(op.tokenFactory.createNativeFunctionToken(...attrWriter(attr)), op.cvp.methodsVar(base, `${attr}=`));
22490
22463
  }
22491
22464
  var module_default = {
22492
22465
  newInstance({ op, cd }) {
@@ -22499,28 +22472,24 @@ var module_default = {
22499
22472
  prepend: include.bind(void 0, "prepend"),
22500
22473
  alias_method({ op, base, cd }) {
22501
22474
  if (!base.isClassLikeToken())
22502
- throw new Error(
22503
- `Module#alias_method is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`
22504
- );
22505
- if (cd.arguments?.pSplat) op.a.warnUnsupported(cd.callNode, "Module#alias_method called with splat arguments");
22475
+ throw new Error(`Module#alias_method is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`);
22476
+ if (cd.arguments?.pSplat)
22477
+ op.a.warnUnsupported(cd.callNode, "Module#alias_method called with splat arguments");
22506
22478
  const pos = cd.arguments?.positional;
22507
22479
  if (pos?.length !== 2) {
22508
22480
  op.a.warnUnsupported(cd.callNode, "Module#alias_method called with incorrect number of positional arguments");
22509
22481
  return;
22510
22482
  }
22511
22483
  const lArgs = pos.map((a) => literalArg(op, cd, a, "Module#alias_method"));
22512
- if (lArgs.includes(void 0)) return;
22513
- const [target, source] = lArgs.map(
22514
- (a) => a.type === "symbol" ? a.value.slice(1) : a.value
22515
- );
22484
+ if (lArgs.includes(void 0))
22485
+ return;
22486
+ const [target, source] = lArgs.map((a) => a.type === "symbol" ? a.value.slice(1) : a.value);
22516
22487
  op.solver.addSubsetConstraint(op.cvp.methodsVar(base, source), op.cvp.methodsVar(base, target));
22517
22488
  },
22518
22489
  define_method: unsupported("Module", "define_method"),
22519
22490
  module_function({ op, base, cd }) {
22520
22491
  if (!base.isClassLikeToken())
22521
- throw new Error(
22522
- `Module#module_function is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`
22523
- );
22492
+ throw new Error(`Module#module_function is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`);
22524
22493
  if (base.klass !== op.state.globalNatives.Module)
22525
22494
  return;
22526
22495
  if (isCallNode(cd.callNode) && cd.callNode.receiverNode && !isSelfNode(cd.callNode.receiverNode))
@@ -22528,7 +22497,8 @@ var module_default = {
22528
22497
  const names = [];
22529
22498
  if (!cd.arguments || !("pSplat" in cd.arguments || cd.arguments.positional?.length)) {
22530
22499
  const scope = assertDefined(cd.callNode.closest(["block", "do_block", "module", "program"]));
22531
- if (isModuleNode(scope)) assert4(base.allocSite.endsWith(`::${scope.nameNode.text}`));
22500
+ if (isModuleNode(scope))
22501
+ assert4(base.allocSite.endsWith(`::${scope.nameNode.text}`));
22532
22502
  const endPos = cd.callNode.endPosition;
22533
22503
  for (const [name, startPos] of DefinedMethodsVisitor.getNames(scope, op))
22534
22504
  if (startPos.row > endPos.row || startPos.row === endPos.row && startPos.column >= endPos.column)
@@ -22538,7 +22508,8 @@ var module_default = {
22538
22508
  op.a.warnUnsupported(cd.callNode, "Module#module_function called with splat arguments");
22539
22509
  for (const arg of cd.arguments.positional ?? []) {
22540
22510
  const lArg = literalArg(op, cd, arg, "Module#module_function");
22541
- if (lArg) names.push(lArg.type === "symbol" ? lArg.value.slice(1) : lArg.value);
22511
+ if (lArg)
22512
+ names.push(lArg.type === "symbol" ? lArg.value.slice(1) : lArg.value);
22542
22513
  }
22543
22514
  }
22544
22515
  const sct = op.singletonClass(base);
@@ -22552,12 +22523,11 @@ var module_default = {
22552
22523
  op.a.warnUnsupported(cd.callNode, "Module#const_get on a singleton class");
22553
22524
  return;
22554
22525
  } else if (!base.isClassOrModuleToken())
22555
- throw new Error(
22556
- `Module#const_get is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`
22557
- );
22526
+ throw new Error(`Module#const_get is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`);
22558
22527
  const positional = cd.arguments?.positional;
22559
22528
  const lArg = literalArg(op, cd, positional?.[0], "Module#const_get");
22560
- if (!lArg) return;
22529
+ if (!lArg)
22530
+ return;
22561
22531
  const name = lArg.type === "symbol" ? lArg.value.slice(1) : lArg.value;
22562
22532
  checkConstant(name);
22563
22533
  if (name.startsWith("::")) {
@@ -22568,20 +22538,21 @@ var module_default = {
22568
22538
  const vars = [];
22569
22539
  if (inherit) {
22570
22540
  vars.push(op.cvp.ancestorsVar(base));
22571
- if (base.klass === op.state.globalNatives.Module) vars.push(op.cvp.ancestorsVar(op.state.globalNatives.Object));
22572
- } else vars.push(base);
22541
+ if (base.klass === op.state.globalNatives.Module)
22542
+ vars.push(op.cvp.ancestorsVar(op.state.globalNatives.Object));
22543
+ } else
22544
+ vars.push(base);
22573
22545
  for (const v of vars)
22574
- op.addForAllTokensConstraint(v, 17 /* NATIVE_MODULE_CONST_GET */, { n: cd.callNode }, (t15) => {
22546
+ op.addForAllTokensConstraint(v, TokenListener.NATIVE_MODULE_CONST_GET, { n: cd.callNode }, (t15) => {
22575
22547
  if (t15 instanceof ObjectToken) {
22576
22548
  if (t15 instanceof SingletonClassToken)
22577
22549
  op.a.warnUnsupported(cd.callNode, "Module#const_get called with a singleton class ancestor");
22578
22550
  else if (t15.isClassOrModuleToken())
22579
22551
  op.solver.addSubsetConstraint(op.cvp.constantVar(makeConstant(`${t15.allocSite}::${name}`)), cd.result);
22580
22552
  else
22581
- throw new Error(
22582
- `Module#const_get is called with a non-Class or Module token ${t15} at ${nodeToString(cd.callNode)}`
22583
- );
22584
- } else t15;
22553
+ throw new Error(`Module#const_get is called with a non-Class or Module token ${t15} at ${nodeToString(cd.callNode)}`);
22554
+ } else
22555
+ t15;
22585
22556
  });
22586
22557
  },
22587
22558
  const_set({ op, base, cd }) {
@@ -22589,19 +22560,21 @@ var module_default = {
22589
22560
  op.a.warnUnsupported(cd.callNode, "Module#const_set on a singleton class");
22590
22561
  return;
22591
22562
  } else if (!base.isClassOrModuleToken())
22592
- throw new Error(
22593
- `Module#const_set is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`
22594
- );
22563
+ throw new Error(`Module#const_set is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`);
22595
22564
  const pos = cd.arguments?.positional;
22596
22565
  const value = pos?.[1];
22597
- if (!(value instanceof ConstraintVar || value instanceof TokenInterface)) return;
22598
- if (cd.result) op.inclusionConstraint(value, cd.result);
22566
+ if (!(value instanceof ConstraintVar || value instanceof TokenInterface))
22567
+ return;
22568
+ if (cd.result)
22569
+ op.inclusionConstraint(value, cd.result);
22599
22570
  const lArg = literalArg(op, cd, pos[0], "Module#const_set");
22600
- if (!lArg) return;
22571
+ if (!lArg)
22572
+ return;
22601
22573
  const name = lArg.type === "symbol" ? lArg.value.slice(1) : lArg.value;
22602
22574
  if (/^[A-Z][^:]*$/.test(name))
22603
22575
  op.inclusionConstraint(value, op.cvp.constantVar(makeConstant(`${base.allocSite}::${name}`)));
22604
- else op.a.warnUnsupported(cd.callNode, "Module#const_set with invalid constant name");
22576
+ else
22577
+ op.a.warnUnsupported(cd.callNode, "Module#const_set with invalid constant name");
22605
22578
  },
22606
22579
  attr: unsupported("Module", "attr"),
22607
22580
  attr_reader: attrModel.bind(void 0, "reader"),
@@ -22609,9 +22582,7 @@ var module_default = {
22609
22582
  attr_accessor: attrModel.bind(void 0, "accessor"),
22610
22583
  module_eval({ op, base, cd }) {
22611
22584
  if (!base.isClassLikeToken())
22612
- throw new Error(
22613
- `Module#module_eval is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`
22614
- );
22585
+ throw new Error(`Module#module_eval is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`);
22615
22586
  const pos = cd.arguments?.positional;
22616
22587
  if (pos?.length) {
22617
22588
  const a = pos[0];
@@ -22619,34 +22590,21 @@ var module_default = {
22619
22590
  op.a.warnUnsupported(cd.callNode, "Module#module_eval with dynamically computed argument");
22620
22591
  else if (a.type === "string")
22621
22592
  op.a.warnUnsupported(cd.callNode, "Module#module_eval with statically known string argument");
22622
- else op.a.warnUnsupported(cd.callNode, `Module#module_eval with ${a.type} argument`);
22593
+ else
22594
+ op.a.warnUnsupported(cd.callNode, `Module#module_eval with ${a.type} argument`);
22623
22595
  return;
22624
22596
  }
22625
- invokeBlock(
22626
- cd.arguments?.block,
22627
- 13 /* NATIVE_MODULE_MODULE_EVAL */,
22628
- // Functions defined in the block are defined on the module itself
22597
+ invokeBlock(cd.arguments?.block, TokenListener.NATIVE_MODULE_MODULE_EVAL, base, {
22598
+ op,
22629
22599
  base,
22630
- {
22631
- op,
22632
- base,
22633
- cd: { ...cd, arguments: { positional: [base] } }
22634
- }
22635
- );
22600
+ cd: { ...cd, arguments: { positional: [base] } }
22601
+ });
22636
22602
  },
22637
22603
  module_exec({ op, base, cd }) {
22638
22604
  if (!base.isClassLikeToken())
22639
- throw new Error(
22640
- `Module#module_exec is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`
22641
- );
22605
+ throw new Error(`Module#module_exec is called on a non-Class or Module token ${base} at ${nodeToString(cd.callNode)}`);
22642
22606
  const { block, ...args } = cd.arguments ?? {};
22643
- invokeBlock(
22644
- block,
22645
- 15 /* NATIVE_MODULE_MODULE_EXEC */,
22646
- // Functions defined in the block are defined on the module itself
22647
- base,
22648
- { op, base, cd: { ...cd, arguments: args } }
22649
- );
22607
+ invokeBlock(block, TokenListener.NATIVE_MODULE_MODULE_EXEC, base, { op, base, cd: { ...cd, arguments: args } });
22650
22608
  },
22651
22609
  using: unsupported("Module", "using")
22652
22610
  },
@@ -22661,14 +22619,16 @@ var module_default = {
22661
22619
  var attrReader = cache((name) => [
22662
22620
  makeNative(`Module#attr_reader#${name}`),
22663
22621
  ({ op, cd, base }) => {
22664
- if (!(base instanceof ObjectToken)) throw new Error("attr_reader is called on a non-object");
22622
+ if (!(base instanceof ObjectToken))
22623
+ throw new Error("attr_reader is called on a non-object");
22665
22624
  op.solver.addSubsetConstraint(op.cvp.objPropVar(base, `@${name}`), cd.result);
22666
22625
  }
22667
22626
  ]);
22668
22627
  var attrWriter = cache((name) => [
22669
22628
  makeNative(`Module#attr_writer#${name}`),
22670
22629
  ({ op, cd, base }) => {
22671
- if (!(base instanceof ObjectToken)) throw new Error("attr_writer is called on a non-object");
22630
+ if (!(base instanceof ObjectToken))
22631
+ throw new Error("attr_writer is called on a non-object");
22672
22632
  const positional = cd.arguments?.positional;
22673
22633
  if (positional?.length !== 1) {
22674
22634
  op.a.warnUnsupported(cd.callNode, "attr_writer called with incorrect number of positional arguments");
@@ -22676,27 +22636,31 @@ var attrWriter = cache((name) => [
22676
22636
  }
22677
22637
  const arg = positional[0];
22678
22638
  const rVar = op.cvp.objPropVar(base, `@${name}`);
22679
- if (arg instanceof ConstraintVar) op.solver.addSubsetConstraint(arg, rVar);
22680
- else if (arg instanceof ObjectToken) op.solver.addTokenConstraint(arg, rVar);
22681
- else arg;
22639
+ if (arg instanceof ConstraintVar)
22640
+ op.solver.addSubsetConstraint(arg, rVar);
22641
+ else if (arg instanceof ObjectToken)
22642
+ op.solver.addTokenConstraint(arg, rVar);
22643
+ else
22644
+ arg;
22682
22645
  }
22683
22646
  ]);
22684
22647
  var DefinedMethodsVisitor = class _DefinedMethodsVisitor {
22648
+ op;
22649
+ static getNames = cache((scope, op) => {
22650
+ const visitor = new _DefinedMethodsVisitor(op);
22651
+ const v = visitor;
22652
+ if (isBlockNode(scope) || isDoBlockNode(scope) || isModuleNode(scope)) {
22653
+ if (scope.bodyNode)
22654
+ visit(scope.bodyNode, v);
22655
+ } else
22656
+ for (const node of scope.namedChildren)
22657
+ visit(node, v);
22658
+ return visitor.names;
22659
+ }, new NodeMap());
22660
+ names = new Array();
22685
22661
  constructor(op) {
22686
22662
  this.op = op;
22687
22663
  }
22688
- static getNames = cache(
22689
- (scope, op) => {
22690
- const visitor = new _DefinedMethodsVisitor(op);
22691
- const v = visitor;
22692
- if (isBlockNode(scope) || isDoBlockNode(scope) || isModuleNode(scope)) {
22693
- if (scope.bodyNode) visit(scope.bodyNode, v);
22694
- } else for (const node of scope.namedChildren) visit(node, v);
22695
- return visitor.names;
22696
- },
22697
- new NodeMap()
22698
- );
22699
- names = new Array();
22700
22664
  *method(node) {
22701
22665
  this.names.push([node.nameNode.text, node.startPosition]);
22702
22666
  }
@@ -22710,8 +22674,6 @@ var DefinedMethodsVisitor = class _DefinedMethodsVisitor {
22710
22674
  }
22711
22675
  }
22712
22676
  }
22713
- // Stop visitor from going into nested scopes
22714
- /* eslint-disable @typescript-eslint/no-empty-function */
22715
22677
  *singleton_method() {
22716
22678
  }
22717
22679
  *block() {
@@ -22724,10 +22686,9 @@ var DefinedMethodsVisitor = class _DefinedMethodsVisitor {
22724
22686
  }
22725
22687
  *singleton_class() {
22726
22688
  }
22727
- /* eslint-enable @typescript-eslint/no-empty-function */
22728
22689
  };
22729
22690
 
22730
- // ../ruby-analyzer/src/natives/3rd-party/nokogiri.ts
22691
+ // ../ruby-analyzer/dist/natives/3rd-party/nokogiri.js
22731
22692
  var nokogiri_default = {
22732
22693
  "Nokogiri::XML::Node": {
22733
22694
  fake: true
@@ -22736,11 +22697,7 @@ var nokogiri_default = {
22736
22697
  fake: true,
22737
22698
  methods: {
22738
22699
  initialize({ base, op }) {
22739
- op.solver.addTokenConstraint(
22740
- // eslint-disable-next-line unicorn/no-useless-undefined
22741
- op.tokenFactory.createInstanceToken(op.state.globalNatives["Nokogiri::XML::Node"], void 0),
22742
- op.cvp.objPropVar(base, "@root")
22743
- );
22700
+ op.solver.addTokenConstraint(op.tokenFactory.createInstanceToken(op.state.globalNatives["Nokogiri::XML::Node"], void 0), op.cvp.objPropVar(base, "@root"));
22744
22701
  }
22745
22702
  },
22746
22703
  setup(t15, op) {
@@ -22749,32 +22706,27 @@ var nokogiri_default = {
22749
22706
  }
22750
22707
  };
22751
22708
 
22752
- // ../ruby-analyzer/src/natives/3rd-party/rails.ts
22709
+ // ../ruby-analyzer/dist/natives/3rd-party/rails.js
22753
22710
  var rails_default = {
22754
22711
  "Rails::Initializable::ClassMethods": {
22755
22712
  fake: true,
22756
22713
  methods: {
22757
22714
  initializer({ base, op, cd }) {
22758
22715
  const blk = cd.arguments?.block;
22759
- if (!blk) return;
22716
+ if (!blk)
22717
+ return;
22760
22718
  if (!(base instanceof ClassToken)) {
22761
22719
  op.a.warnUnsupported(cd.callNode, "Rails::Initializable::ClassMethods#initializer called on non-Class");
22762
22720
  return;
22763
22721
  }
22764
22722
  const it = op.tokenFactory.createInstanceToken(base, void 0);
22765
- invokeBlock(
22766
- blk,
22767
- 26 /* RAILS_INITIALIZABLE_INITIALIZER */,
22768
- // uses instance_exec under the hood
22769
- op.singletonClass(it),
22770
- { op, base: it, cd: n7(cd, ["arguments"]) }
22771
- );
22723
+ invokeBlock(blk, TokenListener.RAILS_INITIALIZABLE_INITIALIZER, op.singletonClass(it), { op, base: it, cd: n7(cd, ["arguments"]) });
22772
22724
  }
22773
22725
  }
22774
22726
  }
22775
22727
  };
22776
22728
 
22777
- // ../ruby-analyzer/src/natives/models/basic-object.ts
22729
+ // ../ruby-analyzer/dist/natives/models/basic-object.js
22778
22730
  var basic_object_default = {
22779
22731
  methods: {
22780
22732
  instance_eval({ op, base, cd }) {
@@ -22785,10 +22737,11 @@ var basic_object_default = {
22785
22737
  op.a.warnUnsupported(cd.callNode, "BasicObject#instance_eval with dynamically computed argument");
22786
22738
  else if (a.type === "string")
22787
22739
  op.a.warnUnsupported(cd.callNode, "BasicObject#instance_eval with statically known string argument");
22788
- else op.a.warnUnsupported(cd.callNode, `BasicObject#instance_eval with ${a.type} argument`);
22740
+ else
22741
+ op.a.warnUnsupported(cd.callNode, `BasicObject#instance_eval with ${a.type} argument`);
22789
22742
  return;
22790
22743
  }
22791
- invokeBlock(cd.arguments?.block, 22 /* NATIVE_BASIC_OBJECT_INSTANCE_EVAL */, op.singletonClass(base), {
22744
+ invokeBlock(cd.arguments?.block, TokenListener.NATIVE_BASIC_OBJECT_INSTANCE_EVAL, op.singletonClass(base), {
22792
22745
  op,
22793
22746
  base,
22794
22747
  cd: { ...cd, arguments: { positional: [base] } }
@@ -22796,7 +22749,7 @@ var basic_object_default = {
22796
22749
  },
22797
22750
  instance_exec({ op, base, cd }) {
22798
22751
  const { block, ...args } = cd.arguments ?? {};
22799
- invokeBlock(block, 24 /* NATIVE_BASIC_OBJECT_INSTANCE_EXEC */, op.singletonClass(base), {
22752
+ invokeBlock(block, TokenListener.NATIVE_BASIC_OBJECT_INSTANCE_EXEC, op.singletonClass(base), {
22800
22753
  op,
22801
22754
  base,
22802
22755
  cd: { ...cd, arguments: args }
@@ -22805,7 +22758,7 @@ var basic_object_default = {
22805
22758
  }
22806
22759
  };
22807
22760
 
22808
- // ../ruby-analyzer/src/natives/models/kernel.ts
22761
+ // ../ruby-analyzer/dist/natives/models/kernel.js
22809
22762
  import assert5 from "node:assert";
22810
22763
  import fs from "node:fs";
22811
22764
  import { dirname, extname, isAbsolute, join as join2 } from "node:path";
@@ -22816,13 +22769,15 @@ function callProcNew(p) {
22816
22769
  function simpleResolver(root) {
22817
22770
  return (candidate) => {
22818
22771
  const fullPath = join2(root, candidate);
22819
- if (fs.existsSync(fullPath)) return fullPath;
22772
+ if (fs.existsSync(fullPath))
22773
+ return fullPath;
22820
22774
  };
22821
22775
  }
22822
22776
  var cachedResolver = cache((root) => {
22823
22777
  const paths = new Set(globSync2(`**/*.{${requireExtensions.map((ext2) => ext2.slice(1)).join(",")}}`, { cwd: root }));
22824
22778
  return (c) => {
22825
- if (paths.has(c.startsWith("./") ? c.slice(2) : c)) return join2(root, c);
22779
+ if (paths.has(c.startsWith("./") ? c.slice(2) : c))
22780
+ return join2(root, c);
22826
22781
  };
22827
22782
  });
22828
22783
  function loadModule(method, required, roots, candidates, op, cd) {
@@ -22850,12 +22805,7 @@ function requireImpl(method, { op, cd }) {
22850
22805
  const positional = cd.arguments?.positional;
22851
22806
  const arg = positional?.[expectedArgs - 1];
22852
22807
  if (positional?.length !== expectedArgs) {
22853
- logger.error(
22854
- "Kernel#%s called with wrong number of arguments (%d, expected %d)",
22855
- method,
22856
- positional?.length ?? 0,
22857
- expectedArgs
22858
- );
22808
+ logger.error("Kernel#%s called with wrong number of arguments (%d, expected %d)", method, positional?.length ?? 0, expectedArgs);
22859
22809
  return;
22860
22810
  } else if (!arg || arg instanceof ConstraintVar || arg instanceof TokenInterface || arg.type !== "string") {
22861
22811
  op.a.warnUnsupported(cd.callNode, `Kernel#${method} called with non-constant string argument`);
@@ -22871,19 +22821,19 @@ function requireImpl(method, { op, cd }) {
22871
22821
  if (isAbsolute(required)) {
22872
22822
  op.a.warnUnsupported(cd.callNode, `Kernel#${method} called with absolute path: '${required}'`);
22873
22823
  return;
22874
- } else if (explicitlyRelative(required)) requireFrom = [simpleResolver(op.a.rootDir)];
22875
- else requireFrom = op.state.loadPath.map(cachedResolver);
22824
+ } else if (explicitlyRelative(required))
22825
+ requireFrom = [simpleResolver(op.a.rootDir)];
22826
+ else
22827
+ requireFrom = op.state.loadPath.map(cachedResolver);
22876
22828
  }
22877
22829
  loadModule(method, required, requireFrom, candidates, op, cd);
22878
22830
  }
22879
22831
  var globalKernelMethods = {
22880
22832
  eval: unsupported("Kernel", "eval"),
22881
22833
  proc: callProcNew,
22882
- // FIXME: Tag the resulting Proc as a lambda
22883
22834
  lambda: callProcNew,
22884
22835
  require_relative: requireImpl.bind(void 0, "require_relative"),
22885
22836
  require: requireImpl.bind(void 0, "require"),
22886
- // Treat `autoload` is an immediate require, which is sound but (possibly) imprecise
22887
22837
  autoload: requireImpl.bind(void 0, "autoload"),
22888
22838
  load: ({ op, cd }) => {
22889
22839
  const positional = cd.arguments?.positional;
@@ -22898,16 +22848,10 @@ var globalKernelMethods = {
22898
22848
  if (positional.length >= 2 || cd.arguments?.keyword?.some(([name]) => name === "wrap"))
22899
22849
  op.a.warnUnsupported(cd.callNode, "Kernel#load called with 'wrap' argument");
22900
22850
  const required = arg.value;
22901
- if (isAbsolute(required)) op.a.warnUnsupported(cd.callNode, `Kernel#load called with absolute path: '${required}'`);
22851
+ if (isAbsolute(required))
22852
+ op.a.warnUnsupported(cd.callNode, `Kernel#load called with absolute path: '${required}'`);
22902
22853
  else
22903
- loadModule(
22904
- "load",
22905
- required,
22906
- [...explicitlyRelative(required) ? [] : op.state.loadPath.map(cachedResolver), simpleResolver(op.a.rootDir)],
22907
- [required],
22908
- op,
22909
- cd
22910
- );
22854
+ loadModule("load", required, [...explicitlyRelative(required) ? [] : op.state.loadPath.map(cachedResolver), simpleResolver(op.a.rootDir)], [required], op, cd);
22911
22855
  }
22912
22856
  };
22913
22857
  var kernel_default = {
@@ -22919,9 +22863,11 @@ var kernel_default = {
22919
22863
  define_singleton_method({ base, op, cd }) {
22920
22864
  let [nameArg, methodArg] = cd.arguments?.positional ?? [];
22921
22865
  const lNameArg = literalArg(op, cd, nameArg, "Kernel#define_singleton_method");
22922
- if (!lNameArg) return;
22866
+ if (!lNameArg)
22867
+ return;
22923
22868
  if (cd.arguments.positional.length === 1) {
22924
- if ("block" in cd.arguments) methodArg = cd.arguments.block;
22869
+ if ("block" in cd.arguments)
22870
+ methodArg = cd.arguments.block;
22925
22871
  else {
22926
22872
  op.a.warnUnsupported(cd.callNode, "Kernel#define_singleton_method called with wrong number of arguments");
22927
22873
  return;
@@ -22931,109 +22877,104 @@ var kernel_default = {
22931
22877
  op.a.warnUnsupported(cd.callNode, "Kernel#define_singleton_method called with non-object method argument");
22932
22878
  return;
22933
22879
  }
22934
- const mVar = op.cvp.methodsVar(
22935
- op.singletonClass(base),
22936
- lNameArg.type === "symbol" ? lNameArg.value.slice(1) : lNameArg.value
22937
- );
22938
- op.addForAllTokensConstraint(
22939
- methodArg,
22940
- 19 /* NATIVE_KERNEL_DEFINE_SINGLETON_METHOD */,
22941
- { t: base, s: mVar.name },
22942
- (mt) => {
22943
- if (mt instanceof ObjectToken) {
22944
- if (mt instanceof MethodToken)
22945
- op.solver.addForAllTokensConstraint(
22946
- op.cvp.ancestorsVar(op.singletonClass(mt.receiver)),
22947
- 21 /* NATIVE_KERNEL_DEFINE_SINGLETON_METHOD_METHOD */,
22948
- { t: base, s: mVar.name },
22949
- (t15) => {
22950
- if (t15 instanceof ObjectToken) {
22951
- if (!t15.isClassLikeToken()) assert5.fail(`Expected class or module token, got ${t15}`);
22952
- op.solver.addSubsetConstraint(op.cvp.methodsVar(t15, mt.methodName), mVar);
22953
- } else t15;
22954
- }
22955
- );
22956
- else if (mt.klass === op.state.globalNatives.Proc)
22957
- op.solver.addForAllTokensConstraint(
22958
- op.cvp.methodsVar(op.singletonClass(mt), "call"),
22959
- 20 /* NATIVE_KERNEL_DEFINE_SINGLETON_METHOD_PROC */,
22960
- { t: base, s: mVar.name },
22961
- (ft) => {
22962
- if (ft instanceof FunctionToken) {
22963
- assert5(ft.kind !== "method");
22964
- op.solver.addTokenConstraint(ft.toKind("method", op), mVar);
22965
- } else if (ft instanceof NativeFunctionToken) op.solver.addTokenConstraint(ft, mVar);
22966
- else ft;
22967
- }
22968
- );
22969
- else op.a.warnUnsupported(cd.callNode, "Kernel#define_singleton_method got non-Proc/Method token");
22970
- } else {
22971
- mt;
22972
- op.a.warnUnsupported(cd.callNode, "Kernel#define_singleton_method got non-object method token");
22973
- }
22880
+ const mVar = op.cvp.methodsVar(op.singletonClass(base), lNameArg.type === "symbol" ? lNameArg.value.slice(1) : lNameArg.value);
22881
+ op.addForAllTokensConstraint(methodArg, TokenListener.NATIVE_KERNEL_DEFINE_SINGLETON_METHOD, { t: base, s: mVar.name }, (mt) => {
22882
+ if (mt instanceof ObjectToken) {
22883
+ if (mt instanceof MethodToken)
22884
+ op.solver.addForAllTokensConstraint(op.cvp.ancestorsVar(op.singletonClass(mt.receiver)), TokenListener.NATIVE_KERNEL_DEFINE_SINGLETON_METHOD_METHOD, { t: base, s: mVar.name }, (t15) => {
22885
+ if (t15 instanceof ObjectToken) {
22886
+ if (!t15.isClassLikeToken())
22887
+ assert5.fail(`Expected class or module token, got ${t15}`);
22888
+ op.solver.addSubsetConstraint(op.cvp.methodsVar(t15, mt.methodName), mVar);
22889
+ } else
22890
+ t15;
22891
+ });
22892
+ else if (mt.klass === op.state.globalNatives.Proc)
22893
+ op.solver.addForAllTokensConstraint(op.cvp.methodsVar(op.singletonClass(mt), "call"), TokenListener.NATIVE_KERNEL_DEFINE_SINGLETON_METHOD_PROC, { t: base, s: mVar.name }, (ft) => {
22894
+ if (ft instanceof FunctionToken) {
22895
+ assert5(ft.kind !== "method");
22896
+ op.solver.addTokenConstraint(ft.toKind("method", op), mVar);
22897
+ } else if (ft instanceof NativeFunctionToken)
22898
+ op.solver.addTokenConstraint(ft, mVar);
22899
+ else
22900
+ ft;
22901
+ });
22902
+ else
22903
+ op.a.warnUnsupported(cd.callNode, "Kernel#define_singleton_method got non-Proc/Method token");
22904
+ } else {
22905
+ mt;
22906
+ op.a.warnUnsupported(cd.callNode, "Kernel#define_singleton_method got non-object method token");
22974
22907
  }
22975
- );
22908
+ });
22976
22909
  },
22977
22910
  method({ base, op, cd }) {
22978
22911
  const lNameArg = literalArg(op, cd, cd.arguments?.positional?.[0], "Kernel#method");
22979
- if (!lNameArg) return;
22912
+ if (!lNameArg)
22913
+ return;
22980
22914
  const name = lNameArg.type === "symbol" ? lNameArg.value.slice(1) : lNameArg.value;
22981
- op.solver.addTokenConstraint(
22982
- op.tokenFactory.createMethodToken(op.state.globalNatives.Method, base, name),
22983
- cd.result
22984
- );
22915
+ op.solver.addTokenConstraint(op.tokenFactory.createMethodToken(op.state.globalNatives.Method, base, name), cd.result);
22985
22916
  },
22986
22917
  instance_variable_get({ base, op, cd }) {
22987
22918
  const lNameArg = literalArg(op, cd, cd.arguments?.positional?.[0], "Kernel#instance_variable_get");
22988
- if (!lNameArg) return;
22919
+ if (!lNameArg)
22920
+ return;
22989
22921
  const name = lNameArg.type === "symbol" ? lNameArg.value.slice(1) : lNameArg.value;
22990
- if (name.startsWith("@")) op.solver.addSubsetConstraint(op.cvp.objPropVar(base, name), cd.result);
22991
- else op.a.warnUnsupported(cd.callNode, "Kernel#instance_variable_get called with invalid ivar name");
22922
+ if (name.startsWith("@"))
22923
+ op.solver.addSubsetConstraint(op.cvp.objPropVar(base, name), cd.result);
22924
+ else
22925
+ op.a.warnUnsupported(cd.callNode, "Kernel#instance_variable_get called with invalid ivar name");
22992
22926
  },
22993
22927
  instance_variable_set({ base, op, cd }) {
22994
22928
  const valueArg = cd.arguments?.positional?.[1];
22995
- if (!(valueArg instanceof ConstraintVar || valueArg instanceof TokenInterface)) return;
22996
- if (cd.result) op.inclusionConstraint(valueArg, cd.result);
22929
+ if (!(valueArg instanceof ConstraintVar || valueArg instanceof TokenInterface))
22930
+ return;
22931
+ if (cd.result)
22932
+ op.inclusionConstraint(valueArg, cd.result);
22997
22933
  const lNameArg = literalArg(op, cd, cd.arguments?.positional?.[0], "Kernel#instance_variable_set");
22998
- if (!lNameArg) return;
22934
+ if (!lNameArg)
22935
+ return;
22999
22936
  const name = lNameArg.type === "symbol" ? lNameArg.value.slice(1) : lNameArg.value;
23000
- if (name.startsWith("@")) op.inclusionConstraint(valueArg, op.cvp.objPropVar(base, name));
23001
- else op.a.warnUnsupported(cd.callNode, "Kernel#instance_variable_set called with invalid ivar name");
22937
+ if (name.startsWith("@"))
22938
+ op.inclusionConstraint(valueArg, op.cvp.objPropVar(base, name));
22939
+ else
22940
+ op.a.warnUnsupported(cd.callNode, "Kernel#instance_variable_set called with invalid ivar name");
23002
22941
  }
23003
22942
  },
23004
- // TODO: Remove this?
23005
22943
  staticMethods: globalKernelMethods
23006
22944
  };
23007
22945
 
23008
- // ../ruby-analyzer/src/natives/models/object.ts
22946
+ // ../ruby-analyzer/dist/natives/models/object.js
23009
22947
  var object_default = {
23010
22948
  superclass: "BasicObject",
23011
22949
  includes: ["Kernel"],
23012
22950
  methods: {
23013
- // TODO: This is actually defined on Kernel
23014
22951
  extend: ({ base, op, cd }) => {
23015
- if (cd.arguments?.pSplat) op.a.warnUnsupported(cd.callNode, "Object#extend called with splat arguments");
22952
+ if (cd.arguments?.pSplat)
22953
+ op.a.warnUnsupported(cd.callNode, "Object#extend called with splat arguments");
23016
22954
  const av = op.cvp.ancestorsVar(op.singletonClass(base));
23017
22955
  for (const arg of cd.arguments?.positional ?? [])
23018
22956
  if (arg instanceof ConstraintVar || arg instanceof ObjectToken)
23019
- op.addForAllTokensConstraint(arg, 18 /* NATIVE_OBJECT_EXTEND */, { t: base }, (t15) => {
22957
+ op.addForAllTokensConstraint(arg, TokenListener.NATIVE_OBJECT_EXTEND, { t: base }, (t15) => {
23020
22958
  if (t15 instanceof ObjectToken) {
23021
22959
  if (t15.klass === op.state.globalNatives.Module)
23022
22960
  op.solver.addSubsetConstraint(op.cvp.ancestorsVar(t15), av);
23023
- } else t15;
22961
+ } else
22962
+ t15;
23024
22963
  });
23025
- else arg;
22964
+ else
22965
+ arg;
23026
22966
  }
23027
22967
  }
23028
22968
  };
23029
22969
 
23030
- // ../ruby-analyzer/src/natives/models/singleton.ts
22970
+ // ../ruby-analyzer/dist/natives/models/singleton.js
23031
22971
  var singleton_default = {
23032
22972
  Singleton: {
23033
22973
  staticMethods: {
23034
22974
  included({ op, cd }) {
23035
22975
  const klass = cd.arguments?.positional?.[0];
23036
- if (!(klass instanceof ConstraintVar || klass instanceof TokenInterface)) return;
22976
+ if (!(klass instanceof ConstraintVar || klass instanceof TokenInterface))
22977
+ return;
23037
22978
  op.callMethod(klass, "extend", {
23038
22979
  ...cd,
23039
22980
  arguments: {
@@ -23054,7 +22995,7 @@ var singleton_default = {
23054
22995
  }
23055
22996
  };
23056
22997
 
23057
- // ../ruby-analyzer/src/natives/ruby-model.ts
22998
+ // ../ruby-analyzer/dist/natives/ruby-model.js
23058
22999
  var rubyModel = {
23059
23000
  name: "Ruby",
23060
23001
  modules: {
@@ -23081,7 +23022,8 @@ var rubyModel = {
23081
23022
  }))(p);
23082
23023
  if (it) {
23083
23024
  op.solver.addTokenConstraint(it, cd.result);
23084
- if (!isNative) op.state.classInstantiations.push([base.allocSite, cd.callNode, cd.caller]);
23025
+ if (!isNative)
23026
+ op.state.classInstantiations.push([base.allocSite, cd.callNode, cd.caller]);
23085
23027
  op.callMethod(it, "initialize", {
23086
23028
  ...cd,
23087
23029
  result: void 0
@@ -23094,32 +23036,25 @@ var rubyModel = {
23094
23036
  Module: module_default,
23095
23037
  Object: object_default,
23096
23038
  BasicObject: basic_object_default,
23097
- // Proc objects are modelled by sticking a FunctionToken into the "call" method
23098
- // of the Proc instance's singleton class.
23099
23039
  Proc: {
23100
- // eslint-disable-next-line @typescript-eslint/no-empty-function
23101
23040
  newInstance: () => {
23102
23041
  },
23103
23042
  staticMethods: {
23104
23043
  new: ({ op, cd }) => {
23105
- if (cd.result) op.inclusionConstraint(cd.arguments?.block, cd.result);
23044
+ if (cd.result)
23045
+ op.inclusionConstraint(cd.arguments?.block, cd.result);
23106
23046
  }
23107
23047
  }
23108
23048
  },
23109
- // We cannot model Method objects as neatly as Proc objects, as we need to pass on the bound
23110
- // receiver of the Method instead of the Method object itself when the Method is called.
23111
- // Method objects are modelled by the creation of a MethodToken in Kernel#method.
23112
23049
  Method: {
23113
- // eslint-disable-next-line @typescript-eslint/no-empty-function
23114
23050
  newInstance() {
23115
23051
  }
23116
- // TODO: Add a "call" method that passes on the call to the underlying method with the bound receiver
23117
23052
  },
23118
23053
  ...nokogiri_default
23119
23054
  }
23120
23055
  };
23121
23056
 
23122
- // ../ruby-analyzer/src/natives/native-builder.ts
23057
+ // ../ruby-analyzer/dist/natives/native-builder.js
23123
23058
  function makeNative(name) {
23124
23059
  return `%${name}`;
23125
23060
  }
@@ -23135,7 +23070,8 @@ function buildNatives(solver, tokenFactory, cvp) {
23135
23070
  if (name === "Class") {
23136
23071
  ct = rubyClassToken;
23137
23072
  assert6.strictEqual(tokenFactory.canonicalizeToken(ct), ct);
23138
- } else if (objKlass === "Class") ct = tokenFactory.createClassToken(n12);
23073
+ } else if (objKlass === "Class")
23074
+ ct = tokenFactory.createClassToken(n12);
23139
23075
  else {
23140
23076
  objKlass;
23141
23077
  ct = tokenFactory.createInstanceToken(assertDefined(created.Module), n12);
@@ -23145,18 +23081,12 @@ function buildNatives(solver, tokenFactory, cvp) {
23145
23081
  for (const v of [cvp.ancestorsVar(ct), cvp.constantVar(makeConstant(`::${name}`))])
23146
23082
  solver.addTokenConstraint(ct, v);
23147
23083
  for (const [mname, invoke] of "methods" in klass ? Object.entries(klass.methods) : []) {
23148
- solver.addTokenConstraint(
23149
- tokenFactory.createNativeFunctionToken(makeNative(`${name}#${mname}`), invoke),
23150
- cvp.methodsVar(ct, mname)
23151
- );
23084
+ solver.addTokenConstraint(tokenFactory.createNativeFunctionToken(makeNative(`${name}#${mname}`), invoke), cvp.methodsVar(ct, mname));
23152
23085
  }
23153
23086
  if ("staticMethods" in klass) {
23154
23087
  const sct = tokenFactory.createSingletonClassToken(ct);
23155
23088
  for (const [mname, invoke] of Object.entries(klass.staticMethods))
23156
- solver.addTokenConstraint(
23157
- tokenFactory.createNativeFunctionToken(makeNative(`${name}$${mname}`), invoke),
23158
- cvp.methodsVar(sct, mname)
23159
- );
23089
+ solver.addTokenConstraint(tokenFactory.createNativeFunctionToken(makeNative(`${name}$${mname}`), invoke), cvp.methodsVar(sct, mname));
23160
23090
  }
23161
23091
  }
23162
23092
  const finished = created;
@@ -23165,10 +23095,7 @@ function buildNatives(solver, tokenFactory, cvp) {
23165
23095
  const ct = finished[name];
23166
23096
  const superCt = finished["superclass" in klass ? klass.superclass : "Object"];
23167
23097
  solver.addSubsetConstraint(cvp.ancestorsVar(superCt), cvp.ancestorsVar(ct));
23168
- solver.addSubsetConstraint(
23169
- cvp.ancestorsVar(tokenFactory.createSingletonClassToken(superCt)),
23170
- cvp.ancestorsVar(tokenFactory.createSingletonClassToken(ct))
23171
- );
23098
+ solver.addSubsetConstraint(cvp.ancestorsVar(tokenFactory.createSingletonClassToken(superCt)), cvp.ancestorsVar(tokenFactory.createSingletonClassToken(ct)));
23172
23099
  }
23173
23100
  const op = { solver, tokenFactory, cvp };
23174
23101
  for (const [name, klass] of [...t5(rubyModel.modules), ...t5(rubyModel.classes)]) {
@@ -23180,17 +23107,22 @@ function buildNatives(solver, tokenFactory, cvp) {
23180
23107
  solver.addSubsetConstraint(cvp.ancestorsVar(incCt), av);
23181
23108
  }
23182
23109
  }
23183
- if ("setup" in klass) klass.setup(finished[name], op);
23110
+ if ("setup" in klass)
23111
+ klass.setup(finished[name], op);
23184
23112
  }
23185
23113
  return finished;
23186
23114
  }
23187
23115
 
23188
- // ../ruby-analyzer/src/operations.ts
23116
+ // ../ruby-analyzer/dist/operations.js
23189
23117
  import assert7 from "node:assert";
23190
23118
  import fs2 from "node:fs";
23191
23119
  import { basename, dirname as dirname2, relative } from "node:path";
23192
23120
  var gemDirRegex = /^(?<name>[\w-_]+)-(?<version>\d+[^-]*)/;
23193
23121
  var Operations = class {
23122
+ solver;
23123
+ state;
23124
+ constraintVarProducer;
23125
+ tokenFactory;
23194
23126
  constructor(solver, state, constraintVarProducer, tokenFactory) {
23195
23127
  this.solver = solver;
23196
23128
  this.state = state;
@@ -23217,52 +23149,39 @@ var Operations = class {
23217
23149
  const { solver, cvp } = this;
23218
23150
  const onAncestorToken = (baseToken, klass) => {
23219
23151
  if (logger.isDebugEnabled())
23220
- logger.debug(
23221
- `Processing call to method '${methodName}' on ancestor ${klass} of base token ${baseToken} at ${nodeLocationToString(cd.callNode)}`
23222
- );
23223
- solver.addForAllTokensConstraint(
23224
- cvp.methodsVar(klass, methodName),
23225
- 0 /* Call */,
23226
- { n: cd.callNode, s: methodName, t: baseToken },
23227
- (t15) => handleCall.call(this, cd, baseToken, t15)
23228
- );
23152
+ logger.debug(`Processing call to method '${methodName}' on ancestor ${klass} of base token ${baseToken} at ${nodeLocationToString(cd.callNode)}`);
23153
+ solver.addForAllTokensConstraint(cvp.methodsVar(klass, methodName), TokenListener.Call, { n: cd.callNode, s: methodName, t: baseToken }, (t15) => handleCall.call(this, cd, baseToken, t15));
23229
23154
  };
23230
23155
  const onBaseToken = (baseToken) => {
23231
23156
  if (logger.isDebugEnabled())
23232
- logger.debug(
23233
- `Processing call to method '${methodName}' on base token ${baseToken} at ${nodeLocationToString(cd.callNode)}`
23234
- );
23235
- solver.addForAllTokensConstraint(
23236
- cvp.ancestorsVar(this.singletonClass(baseToken)),
23237
- 4 /* CALL_ANCESTORS */,
23238
- { n: cd.callNode, s: methodName, t: baseToken },
23239
- (t15) => {
23240
- if (t15 instanceof ObjectToken) {
23241
- if (!t15.isClassLikeToken()) assert7.fail(`Expected class or module token, got ${t15}`);
23242
- onAncestorToken(baseToken, t15);
23243
- } else {
23244
- t15;
23245
- logger.error(`Unexpected token type in call ancestors: ${t15} at ${nodeLocationToString(cd.callNode)}`);
23246
- }
23157
+ logger.debug(`Processing call to method '${methodName}' on base token ${baseToken} at ${nodeLocationToString(cd.callNode)}`);
23158
+ solver.addForAllTokensConstraint(cvp.ancestorsVar(this.singletonClass(baseToken)), TokenListener.CALL_ANCESTORS, { n: cd.callNode, s: methodName, t: baseToken }, (t15) => {
23159
+ if (t15 instanceof ObjectToken) {
23160
+ if (!t15.isClassLikeToken())
23161
+ assert7.fail(`Expected class or module token, got ${t15}`);
23162
+ onAncestorToken(baseToken, t15);
23163
+ } else {
23164
+ t15;
23165
+ logger.error(`Unexpected token type in call ancestors: ${t15} at ${nodeLocationToString(cd.callNode)}`);
23247
23166
  }
23248
- );
23167
+ });
23249
23168
  };
23250
23169
  if (receiver instanceof ConstraintVar)
23251
- solver.addForAllTokensConstraint(
23252
- receiver,
23253
- 3 /* CALL_BASE */,
23254
- { n: cd.callNode, s: methodName },
23255
- (baseToken) => {
23256
- if (baseToken instanceof ObjectToken) onBaseToken(baseToken);
23257
- else baseToken;
23258
- }
23259
- );
23260
- else onBaseToken(receiver);
23170
+ solver.addForAllTokensConstraint(receiver, TokenListener.CALL_BASE, { n: cd.callNode, s: methodName }, (baseToken) => {
23171
+ if (baseToken instanceof ObjectToken)
23172
+ onBaseToken(baseToken);
23173
+ else
23174
+ baseToken;
23175
+ });
23176
+ else
23177
+ onBaseToken(receiver);
23261
23178
  function handleCall(cd2, base, t15) {
23262
23179
  if (logger.isVerboseEnabled())
23263
23180
  logger.verbose(`Call to ${base}.${methodName} at ${nodeLocationToString(cd2.callNode)} resolved to ${t15}`);
23264
- if (t15 instanceof FunctionToken) this.dispatchCall(t15, base, cd2);
23265
- else if (t15 instanceof NativeFunctionToken) t15.invoke({ base, op: this, cd: cd2 });
23181
+ if (t15 instanceof FunctionToken)
23182
+ this.dispatchCall(t15, base, cd2);
23183
+ else if (t15 instanceof NativeFunctionToken)
23184
+ t15.invoke({ base, op: this, cd: cd2 });
23266
23185
  else {
23267
23186
  t15;
23268
23187
  logger.error(`Unexpected token type in call: ${t15} at ${nodeLocationToString(cd2.callNode)}`);
@@ -23271,12 +23190,7 @@ var Operations = class {
23271
23190
  }
23272
23191
  dispatchCall(t15, base, cd) {
23273
23192
  const { cvp, solver, a } = this;
23274
- solver.callGraph.addEdge(
23275
- cd.callNode,
23276
- cd.caller,
23277
- assertDefined(a.functionInfos.get(t15.fun))
23278
- // kind
23279
- );
23193
+ solver.callGraph.addEdge(cd.callNode, cd.caller, assertDefined(a.functionInfos.get(t15.fun)));
23280
23194
  const args = cd.arguments;
23281
23195
  if (args) {
23282
23196
  const params = t15.parameters?.namedChildren ?? [];
@@ -23284,9 +23198,11 @@ var Operations = class {
23284
23198
  if ((arg instanceof ConstraintVar || arg instanceof TokenInterface) && params[i])
23285
23199
  this.inclusionConstraint(arg, cvp.nodeVar(params[i]));
23286
23200
  }
23287
- if (args.block) this.inclusionConstraint(args.block, cvp.blockParamVar(t15.fun));
23201
+ if (args.block)
23202
+ this.inclusionConstraint(args.block, cvp.blockParamVar(t15.fun));
23288
23203
  }
23289
- if (t15.kind === "method") solver.addTokenConstraint(base, cvp.selfVar(t15.fun));
23204
+ if (t15.kind === "method")
23205
+ solver.addTokenConstraint(base, cvp.selfVar(t15.fun));
23290
23206
  else {
23291
23207
  t15.kind;
23292
23208
  solver.addSubsetConstraint(cvp.selfVar(t15.scope), cvp.selfVar(t15.fun));
@@ -23295,14 +23211,20 @@ var Operations = class {
23295
23211
  solver.addSubsetConstraint(cvp.returnVar(t15.fun), cd.result);
23296
23212
  }
23297
23213
  inclusionConstraint(from, to) {
23298
- if (from === void 0) return;
23299
- if (from instanceof ConstraintVar) this.solver.addSubsetConstraint(from, to);
23300
- else this.solver.addTokenConstraint(from, to);
23214
+ if (from === void 0)
23215
+ return;
23216
+ if (from instanceof ConstraintVar)
23217
+ this.solver.addSubsetConstraint(from, to);
23218
+ else
23219
+ this.solver.addTokenConstraint(from, to);
23301
23220
  }
23302
23221
  addForAllTokensConstraint(v, key, opts, listener) {
23303
- if (v === void 0) return;
23304
- if (v instanceof ConstraintVar) this.solver.addForAllTokensConstraint(v, key, opts, listener);
23305
- else listener(v);
23222
+ if (v === void 0)
23223
+ return;
23224
+ if (v instanceof ConstraintVar)
23225
+ this.solver.addForAllTokensConstraint(v, key, opts, listener);
23226
+ else
23227
+ listener(v);
23306
23228
  }
23307
23229
  evalArg(arg, fallback) {
23308
23230
  if (isStringNode(arg)) {
@@ -23314,57 +23236,51 @@ var Operations = class {
23314
23236
  return { type: "symbol", value: s };
23315
23237
  } else if (isBareSymbolNode(arg) || isDelimitedSymbolNode(arg))
23316
23238
  this.a.warnUnsupported(arg, `${arg.type} arguments in calls`);
23317
- else if (isMethodNode(arg) || isSingletonMethodNode(arg)) return { type: "symbol", value: `:${arg.nameNode.text}` };
23318
- else return fallback?.();
23319
- }
23320
- getContainingGem = cache(
23321
- (dirPath, isEntry) => {
23322
- const dirName = basename(dirPath);
23323
- const entries = fs2.readdirSync(dirPath, { withFileTypes: true });
23324
- const entry = entries.find(
23325
- (entry2) => entry2.isFile() && (entry2.name === "Rakefile" || entry2.name.endsWith(".gemspec")) || // TODO: Check if the directory is on the load path?
23326
- entry2.isDirectory() && entry2.name === "lib"
23327
- );
23328
- if (entry) {
23329
- let name;
23330
- let version;
23331
- const match2 = gemDirRegex.exec(dirName);
23332
- if (match2) ({ name, version } = match2.groups);
23333
- else {
23334
- const e5 = entry.name.endsWith(".gemspec") ? entry : entries.find((e6) => e6.name.endsWith(".gemspec"));
23335
- name = e5?.name.replace(/\.gemspec$/, "");
23336
- }
23337
- if (name !== void 0) return new PackageInfo(name, version, relative(this.a.rootDir, dirPath), isEntry);
23338
- }
23339
- const parent = dirname2(dirPath);
23340
- if (parent === dirPath || dirPath === this.a.rootDir)
23341
- return new PackageInfo(
23342
- "<main>",
23343
- void 0,
23344
- parent === dirPath ? "" : relative(this.a.rootDir, dirPath),
23345
- isEntry
23346
- );
23347
- return this.getContainingGem(parent, isEntry);
23239
+ else if (isMethodNode(arg) || isSingletonMethodNode(arg))
23240
+ return { type: "symbol", value: `:${arg.nameNode.text}` };
23241
+ else
23242
+ return fallback?.();
23243
+ }
23244
+ getContainingGem = cache((dirPath, isEntry) => {
23245
+ const dirName = basename(dirPath);
23246
+ const entries = fs2.readdirSync(dirPath, { withFileTypes: true });
23247
+ const entry = entries.find((entry2) => entry2.isFile() && (entry2.name === "Rakefile" || entry2.name.endsWith(".gemspec")) || entry2.isDirectory() && entry2.name === "lib");
23248
+ if (entry) {
23249
+ let name;
23250
+ let version;
23251
+ const match2 = gemDirRegex.exec(dirName);
23252
+ if (match2)
23253
+ ({ name, version } = match2.groups);
23254
+ else {
23255
+ const e5 = entry.name.endsWith(".gemspec") ? entry : entries.find((e6) => e6.name.endsWith(".gemspec"));
23256
+ name = e5?.name.replace(/\.gemspec$/, "");
23257
+ }
23258
+ if (name !== void 0)
23259
+ return new PackageInfo(name, version, relative(this.a.rootDir, dirPath), isEntry);
23348
23260
  }
23349
- );
23261
+ const parent = dirname2(dirPath);
23262
+ if (parent === dirPath || dirPath === this.a.rootDir)
23263
+ return new PackageInfo("<main>", void 0, parent === dirPath ? "" : relative(this.a.rootDir, dirPath), isEntry);
23264
+ return this.getContainingGem(parent, isEntry);
23265
+ });
23350
23266
  };
23351
23267
 
23352
- // ../ruby-analyzer/src/parser.ts
23268
+ // ../ruby-analyzer/dist/parser.js
23353
23269
  import Parser from "tree-sitter";
23354
23270
  import Ruby from "tree-sitter-ruby";
23355
23271
  var parser = new Parser();
23356
23272
  parser.setLanguage(Ruby);
23357
23273
 
23358
- // ../ruby-analyzer/src/ruby-ast-visitor.ts
23274
+ // ../ruby-analyzer/dist/ruby-ast-visitor.js
23359
23275
  import assert8 from "node:assert";
23360
23276
 
23361
- // ../ruby-analyzer/src/ruby-vulnerabilities.ts
23277
+ // ../ruby-analyzer/dist/ruby-vulnerabilities.js
23362
23278
  var reFQN = /^(?:(?:<<\w*|\w+)(?:::(?:<<\w*|\w+))*)?#(?:(?:\w+|\?)\.)?[^\t\n .]+$/;
23363
23279
  function validateVulnerabilityID(id) {
23364
23280
  return reFQN.test(id);
23365
23281
  }
23366
23282
 
23367
- // ../ruby-analyzer/src/types/ruby-ast-helper-types.ts
23283
+ // ../ruby-analyzer/dist/types/ruby-ast-helper-types.js
23368
23284
  var functionTypes = ["method", "singleton_method", "block", "do_block"];
23369
23285
  var functionTypeSet = new Set(functionTypes);
23370
23286
  function isFunctionNode(node) {
@@ -23373,20 +23289,23 @@ function isFunctionNode(node) {
23373
23289
  var scopeTypes = [...functionTypes, "class", "singleton_class", "module", "program"];
23374
23290
  var scopeTypeSet = new Set(scopeTypes);
23375
23291
 
23376
- // ../ruby-analyzer/src/ruby-ast-visitor.ts
23292
+ // ../ruby-analyzer/dist/ruby-ast-visitor.js
23377
23293
  function isFullyQualifiedConstant(s) {
23378
23294
  return s.startsWith("::");
23379
23295
  }
23380
23296
  var RubyAstVisitor = class {
23297
+ op;
23298
+ moduleInfo;
23299
+ bindings;
23300
+ done = false;
23301
+ constantNesting = [];
23302
+ scopes = [];
23303
+ handledConstants = new NodeSet();
23381
23304
  constructor(op, moduleInfo, bindings) {
23382
23305
  this.op = op;
23383
23306
  this.moduleInfo = moduleInfo;
23384
23307
  this.bindings = bindings;
23385
23308
  }
23386
- done = false;
23387
- constantNesting = [];
23388
- scopes = [];
23389
- handledConstants = new NodeSet();
23390
23309
  getSurroundingScope() {
23391
23310
  return assertDefined(this.scopes.at(-1));
23392
23311
  }
@@ -23398,20 +23317,17 @@ var RubyAstVisitor = class {
23398
23317
  const i = nesting.findLastIndex((c) => c.startsWith("::"));
23399
23318
  return i === -1 ? makeConstant(`::${nesting.join("::")}`) : makeConstant(nesting.slice(i).join("::"));
23400
23319
  }
23401
- /* Helper to set up constraints for constants and scope resolution nodes. */
23402
23320
  expVar(n12) {
23403
23321
  assert8(!this.done, "expVar called after visitor is done");
23404
- const {
23405
- op: { solver, cvp },
23406
- constantNesting,
23407
- handledConstants
23408
- } = this;
23409
- if (isIdentifierNode(n12)) return cvp.identVar(n12, this.bindings);
23322
+ const { op: { solver, cvp }, constantNesting, handledConstants } = this;
23323
+ if (isIdentifierNode(n12))
23324
+ return cvp.identVar(n12, this.bindings);
23410
23325
  else if (isScopeResolutionNode(n12) || isConstantNode(n12)) {
23411
23326
  const nvar = cvp.nodeVar(n12);
23412
23327
  if (!handledConstants.has(n12)) {
23413
23328
  const c = n12.text;
23414
- if (isFullyQualifiedConstant(c)) solver.addSubsetConstraint(cvp.constantVar(makeConstant(c)), nvar);
23329
+ if (isFullyQualifiedConstant(c))
23330
+ solver.addSubsetConstraint(cvp.constantVar(makeConstant(c)), nvar);
23415
23331
  else {
23416
23332
  for (let i = 0; i <= constantNesting.length; i++) {
23417
23333
  const fq = this.fqConstant([...constantNesting.slice(0, i), c]);
@@ -23421,42 +23337,31 @@ var RubyAstVisitor = class {
23421
23337
  const classOrModule = assertDefined(this.scopes.findLast((s) => isClassNode(s) || isModuleNode(s)));
23422
23338
  assert8.strictEqual(classOrModule.nameNode.text, constantNesting.at(-1));
23423
23339
  const ct = this.classOrModuleToken(this.fqConstant(), classOrModule);
23424
- solver.addForAllTokensConstraint(
23425
- cvp.ancestorsVar(ct),
23426
- 8 /* CONSTANTS_ANCESTORS */,
23427
- { n: n12 },
23428
- (t15) => {
23429
- if (t15 instanceof ObjectToken) {
23430
- if (!t15.isClassOrModuleToken()) assert8.fail(`Expected class or module token, got ${t15}`);
23431
- const fq = makeConstant(`${t15.allocSite}::${c}`);
23432
- solver.addSubsetConstraint(cvp.constantVar(fq), nvar);
23433
- } else t15;
23434
- }
23435
- );
23340
+ solver.addForAllTokensConstraint(cvp.ancestorsVar(ct), TokenListener.CONSTANTS_ANCESTORS, { n: n12 }, (t15) => {
23341
+ if (t15 instanceof ObjectToken) {
23342
+ if (!t15.isClassOrModuleToken())
23343
+ assert8.fail(`Expected class or module token, got ${t15}`);
23344
+ const fq = makeConstant(`${t15.allocSite}::${c}`);
23345
+ solver.addSubsetConstraint(cvp.constantVar(fq), nvar);
23346
+ } else
23347
+ t15;
23348
+ });
23436
23349
  }
23437
23350
  }
23438
23351
  handledConstants.add(n12);
23439
23352
  }
23440
23353
  return nvar;
23441
- } else if (isSelfNode(n12)) return cvp.selfVar(this.getSurroundingScope());
23442
- else if (isParenthesizedStatementsNode(n12)) return n12.lastNamedChild ? this.expVar(n12.lastNamedChild) : void 0;
23443
- else if (isIfModifierNode(n12) || isUnlessModifierNode(n12)) return this.expVar(n12.bodyNode);
23354
+ } else if (isSelfNode(n12))
23355
+ return cvp.selfVar(this.getSurroundingScope());
23356
+ else if (isParenthesizedStatementsNode(n12))
23357
+ return n12.lastNamedChild ? this.expVar(n12.lastNamedChild) : void 0;
23358
+ else if (isIfModifierNode(n12) || isUnlessModifierNode(n12))
23359
+ return this.expVar(n12.bodyNode);
23444
23360
  return cvp.nodeVar(n12);
23445
23361
  }
23446
23362
  *program(node) {
23447
- const {
23448
- op: {
23449
- solver,
23450
- cvp,
23451
- tokenFactory,
23452
- state: { globalNatives }
23453
- },
23454
- scopes
23455
- } = this;
23456
- solver.addTokenConstraint(
23457
- tokenFactory.createInstanceToken(globalNatives.Object, makeNative("main")),
23458
- cvp.selfVar(node)
23459
- );
23363
+ const { op: { solver, cvp, tokenFactory, state: { globalNatives } }, scopes } = this;
23364
+ solver.addTokenConstraint(tokenFactory.createInstanceToken(globalNatives.Object, makeNative("main")), cvp.selfVar(node));
23460
23365
  solver.addTokenConstraint(globalNatives.Object, cvp.defaultDefineeVar(node));
23461
23366
  scopes.push(node);
23462
23367
  yield* node.namedChildren;
@@ -23490,14 +23395,8 @@ var RubyAstVisitor = class {
23490
23395
  this.handleCall(node, this.op.cvp.blockParamVar(meth), "call", this.parseArgumentList(node.firstNamedChild));
23491
23396
  }
23492
23397
  call(node) {
23493
- const methodName = node.methodNode?.text ?? // E.() is syntactic sugar for E.call()
23494
- (assert8.strictEqual(node.operatorNode?.text, "."), "call");
23495
- this.handleCall(
23496
- node,
23497
- node.receiverNode ? assertDefined(this.expVar(node.receiverNode)) : this.op.cvp.selfVar(this.getSurroundingScope()),
23498
- methodName,
23499
- this.parseArgumentList(node.argumentsNode, this.blockToProc(node))
23500
- );
23398
+ const methodName = node.methodNode?.text ?? (assert8.strictEqual(node.operatorNode?.text, "."), "call");
23399
+ this.handleCall(node, node.receiverNode ? assertDefined(this.expVar(node.receiverNode)) : this.op.cvp.selfVar(this.getSurroundingScope()), methodName, this.parseArgumentList(node.argumentsNode, this.blockToProc(node)));
23501
23400
  }
23502
23401
  blockToProc(node) {
23503
23402
  const { op } = this;
@@ -23505,7 +23404,8 @@ var RubyAstVisitor = class {
23505
23404
  let blockNode;
23506
23405
  let kind = "proc";
23507
23406
  if (isCallNode(node)) {
23508
- if (!node.blockNode) return;
23407
+ if (!node.blockNode)
23408
+ return;
23509
23409
  blockNode = node.blockNode;
23510
23410
  } else {
23511
23411
  node.type;
@@ -23515,10 +23415,7 @@ var RubyAstVisitor = class {
23515
23415
  }
23516
23416
  const procToken = op.tokenFactory.createInstanceToken(op.state.globalNatives.Proc, node);
23517
23417
  const sct = op.tokenFactory.createSingletonClassToken(procToken);
23518
- op.solver.addTokenConstraint(
23519
- op.tokenFactory.createFunctionToken(blockNode, kind, this.getSurroundingScope(), parametersNode),
23520
- op.cvp.methodsVar(sct, "call")
23521
- );
23418
+ op.solver.addTokenConstraint(op.tokenFactory.createFunctionToken(blockNode, kind, this.getSurroundingScope(), parametersNode), op.cvp.methodsVar(sct, "call"));
23522
23419
  return procToken;
23523
23420
  }
23524
23421
  handleCall(node, receiver, methodName, args) {
@@ -23544,31 +23441,33 @@ var RubyAstVisitor = class {
23544
23441
  this.registerFunctionInfo(name, node);
23545
23442
  const scopeDefinee = cvp.defaultDefineeVar(scope);
23546
23443
  solver.addSubsetEdge(scopeDefinee, cvp.defaultDefineeVar(node));
23547
- solver.addForAllTokensConstraint(
23548
- // TODO: Warn if definee var is empty
23549
- node.type === "method" ? scopeDefinee : this.expVar(node.objectNode),
23550
- 1 /* Method */,
23551
- { n: node },
23552
- (t15) => {
23553
- if (t15 instanceof ObjectToken) {
23554
- if (node.type === "singleton_method") t15 = op.singletonClass(t15);
23555
- if (t15.isClassLikeToken()) solver.addTokenConstraint(functionToken, cvp.methodsVar(t15, name));
23556
- else logger.error(`Unexpected class of default definee: ${t15.klass} for method ${name}`);
23557
- } else t15;
23558
- }
23559
- );
23560
- if (node.type === "singleton_method") yield node.objectNode;
23444
+ solver.addForAllTokensConstraint(node.type === "method" ? scopeDefinee : this.expVar(node.objectNode), TokenListener.Method, { n: node }, (t15) => {
23445
+ if (t15 instanceof ObjectToken) {
23446
+ if (node.type === "singleton_method")
23447
+ t15 = op.singletonClass(t15);
23448
+ if (t15.isClassLikeToken())
23449
+ solver.addTokenConstraint(functionToken, cvp.methodsVar(t15, name));
23450
+ else
23451
+ logger.error(`Unexpected class of default definee: ${t15.klass} for method ${name}`);
23452
+ } else
23453
+ t15;
23454
+ });
23455
+ if (node.type === "singleton_method")
23456
+ yield node.objectNode;
23561
23457
  scopes.push(node);
23562
23458
  this.addLastNodeToReturnVarConstraint(node);
23563
- if (node.bodyNode) yield node.bodyNode;
23564
- if (node.parametersNode) yield node.parametersNode;
23459
+ if (node.bodyNode)
23460
+ yield node.bodyNode;
23461
+ if (node.parametersNode)
23462
+ yield node.parametersNode;
23565
23463
  scopes.pop();
23566
23464
  }
23567
23465
  block_parameter(node) {
23568
23466
  const { solver, cvp } = this.op;
23569
23467
  const scope = this.getSurroundingScope();
23570
23468
  assert8(isFunctionNode(scope), "Block parameter not in function scope");
23571
- if (node.nameNode) solver.addSubsetConstraint(cvp.blockParamVar(scope), cvp.identVar(node.nameNode, this.bindings));
23469
+ if (node.nameNode)
23470
+ solver.addSubsetConstraint(cvp.blockParamVar(scope), cvp.identVar(node.nameNode, this.bindings));
23572
23471
  }
23573
23472
  lambda(node) {
23574
23473
  const { op } = this;
@@ -23597,7 +23496,8 @@ var RubyAstVisitor = class {
23597
23496
  *handleAssignment(node, operator) {
23598
23497
  const { solver, cvp, a } = this.op;
23599
23498
  yield node.rightNode;
23600
- if (!["=", "&&=", "||="].includes(operator)) return;
23499
+ if (!["=", "&&=", "||="].includes(operator))
23500
+ return;
23601
23501
  const nVar = cvp.nodeVar(node);
23602
23502
  const eVar = this.expVar(node.rightNode);
23603
23503
  const isLogical = operator !== "=";
@@ -23605,15 +23505,18 @@ var RubyAstVisitor = class {
23605
23505
  if (isIdentifierNode(node.leftNode)) {
23606
23506
  const lVar = cvp.identVar(node.leftNode, this.bindings);
23607
23507
  solver.addSubsetConstraint(eVar, lVar);
23608
- if (isLogical) solver.addSubsetConstraint(lVar, nVar);
23508
+ if (isLogical)
23509
+ solver.addSubsetConstraint(lVar, nVar);
23609
23510
  } else if (isInstanceVariableNode(node.leftNode)) {
23610
23511
  const selfVar = cvp.selfVar(this.getSurroundingScope());
23611
- solver.addForAllTokensConstraint(selfVar, 10 /* ASSIGN_INSTANCE_VAR */, { n: node }, (t15) => {
23512
+ solver.addForAllTokensConstraint(selfVar, TokenListener.ASSIGN_INSTANCE_VAR, { n: node }, (t15) => {
23612
23513
  if (t15 instanceof ObjectToken) {
23613
23514
  const oVar = cvp.objPropVar(t15, node.leftNode.text);
23614
23515
  solver.addSubsetConstraint(eVar, oVar);
23615
- if (isLogical) solver.addSubsetConstraint(oVar, nVar);
23616
- } else t15;
23516
+ if (isLogical)
23517
+ solver.addSubsetConstraint(oVar, nVar);
23518
+ } else
23519
+ t15;
23617
23520
  });
23618
23521
  } else if (isCallNode(node.leftNode)) {
23619
23522
  const call = node.leftNode;
@@ -23634,7 +23537,6 @@ var RubyAstVisitor = class {
23634
23537
  callNode: node,
23635
23538
  arguments: { positional: [eVar] },
23636
23539
  result: void 0
23637
- // the result of an assignment is the value assigned, not the result of the setter method
23638
23540
  });
23639
23541
  } else if (isConstantNode(node.leftNode) || isScopeResolutionNode(node.leftNode)) {
23640
23542
  checkConstant(node.leftNode.text);
@@ -23642,15 +23544,18 @@ var RubyAstVisitor = class {
23642
23544
  solver.addSubsetConstraint(eVar, cvp.constantVar(name));
23643
23545
  if (isLogical)
23644
23546
  solver.addSubsetConstraint(this.expVar(node.leftNode), nVar);
23645
- } else a.warnUnsupported(node, `${node.leftNode.type} left-hand side in assignment`);
23547
+ } else
23548
+ a.warnUnsupported(node, `${node.leftNode.type} left-hand side in assignment`);
23646
23549
  }
23647
23550
  instance_variable(node) {
23648
23551
  const { solver, cvp } = this.op;
23649
23552
  const selfVar = cvp.selfVar(this.getSurroundingScope());
23650
23553
  const resVar = cvp.nodeVar(node);
23651
- solver.addForAllTokensConstraint(selfVar, 9 /* READ_INSTANCE_VAR */, { n: node }, (t15) => {
23652
- if (t15 instanceof ObjectToken) solver.addSubsetConstraint(cvp.objPropVar(t15, node.text), resVar);
23653
- else t15;
23554
+ solver.addForAllTokensConstraint(selfVar, TokenListener.READ_INSTANCE_VAR, { n: node }, (t15) => {
23555
+ if (t15 instanceof ObjectToken)
23556
+ solver.addSubsetConstraint(cvp.objPropVar(t15, node.text), resVar);
23557
+ else
23558
+ t15;
23654
23559
  });
23655
23560
  }
23656
23561
  class_variable(node) {
@@ -23661,16 +23566,20 @@ var RubyAstVisitor = class {
23661
23566
  }
23662
23567
  return(node) {
23663
23568
  const { solver, cvp } = this.op;
23664
- if (node.namedChildCount === 0) return;
23569
+ if (node.namedChildCount === 0)
23570
+ return;
23665
23571
  const argumentsListOfReturnNode = node.firstNamedChild;
23666
23572
  const valueToReturnNode = assertDefined(argumentsListOfReturnNode.firstNamedChild);
23667
23573
  const resultVar = this.expVar(valueToReturnNode);
23668
23574
  const enclosingFunction = this.scopes.findLast((n12) => {
23669
- if (isMethodNode(n12) || isSingletonMethodNode(n12)) return true;
23575
+ if (isMethodNode(n12) || isSingletonMethodNode(n12))
23576
+ return true;
23670
23577
  return (isBlockNode(n12) || isDoBlockNode(n12)) && isLambdaNode(n12.parent) && n12.parent.bodyNode.id === n12.id;
23671
23578
  });
23672
- if (enclosingFunction) solver.addSubsetConstraint(resultVar, cvp.returnVar(enclosingFunction));
23673
- else logger.warn(`Return at ${nodeLocationToString(node)} not enclosed in a function`);
23579
+ if (enclosingFunction)
23580
+ solver.addSubsetConstraint(resultVar, cvp.returnVar(enclosingFunction));
23581
+ else
23582
+ logger.warn(`Return at ${nodeLocationToString(node)} not enclosed in a function`);
23674
23583
  }
23675
23584
  module(node) {
23676
23585
  return this.handleClassOrModule(node);
@@ -23679,16 +23588,7 @@ var RubyAstVisitor = class {
23679
23588
  return this.handleClassOrModule(node);
23680
23589
  }
23681
23590
  *handleClassOrModule(node) {
23682
- const {
23683
- op: {
23684
- solver,
23685
- cvp,
23686
- state: { globalNatives, constantsToNodes },
23687
- tokenFactory
23688
- },
23689
- scopes,
23690
- constantNesting
23691
- } = this;
23591
+ const { op: { solver, cvp, state: { globalNatives, constantsToNodes }, tokenFactory }, scopes, constantNesting } = this;
23692
23592
  const n12 = node.nameNode.text;
23693
23593
  checkConstant(n12);
23694
23594
  constantNesting.push(n12);
@@ -23706,20 +23606,17 @@ var RubyAstVisitor = class {
23706
23606
  const sctAv = cvp.ancestorsVar(tokenFactory.createSingletonClassToken(ct));
23707
23607
  constantNesting.pop();
23708
23608
  assert8.strictEqual(node.superclassNode.namedChildCount, 1);
23709
- solver.addForAllTokensConstraint(
23710
- this.expVar(node.superclassNode.firstNamedChild),
23711
- 5 /* SUPERCLASSES */,
23712
- { n: node },
23713
- (t15) => {
23714
- if (t15 instanceof ClassToken) {
23715
- solver.addSubsetConstraint(cvp.ancestorsVar(t15), av);
23716
- solver.addSubsetConstraint(cvp.ancestorsVar(tokenFactory.createSingletonClassToken(t15)), sctAv);
23717
- } else t15;
23718
- }
23719
- );
23609
+ solver.addForAllTokensConstraint(this.expVar(node.superclassNode.firstNamedChild), TokenListener.SUPERCLASSES, { n: node }, (t15) => {
23610
+ if (t15 instanceof ClassToken) {
23611
+ solver.addSubsetConstraint(cvp.ancestorsVar(t15), av);
23612
+ solver.addSubsetConstraint(cvp.ancestorsVar(tokenFactory.createSingletonClassToken(t15)), sctAv);
23613
+ } else
23614
+ t15;
23615
+ });
23720
23616
  yield node.superclassNode;
23721
23617
  constantNesting.push(n12);
23722
- } else solver.addSubsetConstraint(cvp.ancestorsVar(globalNatives.Object), av);
23618
+ } else
23619
+ solver.addSubsetConstraint(cvp.ancestorsVar(globalNatives.Object), av);
23723
23620
  this.op.callMethod(av, "inherited", {
23724
23621
  callNode: node,
23725
23622
  caller: this.caller(node),
@@ -23735,23 +23632,17 @@ var RubyAstVisitor = class {
23735
23632
  constantNesting.pop();
23736
23633
  }
23737
23634
  *singleton_class(node) {
23738
- const {
23739
- op: { solver, cvp },
23740
- scopes
23741
- } = this;
23635
+ const { op: { solver, cvp }, scopes } = this;
23742
23636
  const defaultDefineeVar = cvp.defaultDefineeVar(node);
23743
23637
  const selfVar = cvp.selfVar(node);
23744
- solver.addForAllTokensConstraint(
23745
- this.expVar(node.valueNode),
23746
- 7 /* SINGLETON_CLASS */,
23747
- { n: node },
23748
- (t15) => {
23749
- if (t15 instanceof ObjectToken) {
23750
- const sct = this.op.singletonClass(t15);
23751
- for (const v of [defaultDefineeVar, selfVar]) solver.addTokenConstraint(sct, v);
23752
- } else t15;
23753
- }
23754
- );
23638
+ solver.addForAllTokensConstraint(this.expVar(node.valueNode), TokenListener.SINGLETON_CLASS, { n: node }, (t15) => {
23639
+ if (t15 instanceof ObjectToken) {
23640
+ const sct = this.op.singletonClass(t15);
23641
+ for (const v of [defaultDefineeVar, selfVar])
23642
+ solver.addTokenConstraint(sct, v);
23643
+ } else
23644
+ t15;
23645
+ });
23755
23646
  yield node.valueNode;
23756
23647
  if (node.bodyNode) {
23757
23648
  scopes.push(node);
@@ -23762,7 +23653,8 @@ var RubyAstVisitor = class {
23762
23653
  rescue_modifier(node) {
23763
23654
  const { cvp, solver } = this.op;
23764
23655
  const nVar = cvp.nodeVar(node);
23765
- for (const n12 of [node.bodyNode, node.handlerNode]) solver.addSubsetConstraint(this.expVar(n12), nVar);
23656
+ for (const n12 of [node.bodyNode, node.handlerNode])
23657
+ solver.addSubsetConstraint(this.expVar(n12), nVar);
23766
23658
  }
23767
23659
  alias(node) {
23768
23660
  this.op.a.warnUnsupported(node, "alias");
@@ -23784,15 +23676,16 @@ var RubyAstVisitor = class {
23784
23676
  if(node) {
23785
23677
  const nVar = this.op.cvp.nodeVar(node);
23786
23678
  for (const n12 of [node.consequenceNode, node.alternativeNode])
23787
- if (n12) this.op.solver.addSubsetConstraint(this.expVar(n12), nVar);
23679
+ if (n12)
23680
+ this.op.solver.addSubsetConstraint(this.expVar(n12), nVar);
23788
23681
  }
23789
23682
  elsif(node) {
23790
23683
  this.if(node);
23791
23684
  }
23792
- // eslint-disable-next-line unicorn/no-thenable
23793
23685
  then(node) {
23794
23686
  const val = node.lastNamedChild;
23795
- if (val) this.op.solver.addSubsetConstraint(this.expVar(val), this.op.cvp.nodeVar(node));
23687
+ if (val)
23688
+ this.op.solver.addSubsetConstraint(this.expVar(val), this.op.cvp.nodeVar(node));
23796
23689
  }
23797
23690
  else(node) {
23798
23691
  this.then(node);
@@ -23800,12 +23693,14 @@ var RubyAstVisitor = class {
23800
23693
  addLastNodeToReturnVarConstraint(node) {
23801
23694
  const { solver, cvp } = this.op;
23802
23695
  const lastNode = getLastNodeInFunction(node);
23803
- if (!lastNode) return;
23696
+ if (!lastNode)
23697
+ return;
23804
23698
  solver.addSubsetConstraint(this.expVar(lastNode), cvp.returnVar(node));
23805
23699
  }
23806
23700
  caller(node) {
23807
23701
  const enclosingFunction = this.scopes.findLast((node2) => isFunctionNode(node2));
23808
- if (!enclosingFunction) return this.moduleInfo;
23702
+ if (!enclosingFunction)
23703
+ return this.moduleInfo;
23809
23704
  const caller = this.op.a.functionInfos.get(enclosingFunction);
23810
23705
  if (!caller)
23811
23706
  throw new Error(`Missing function info for ${nodeToString(enclosingFunction)} at ${nodeToString(node)}`);
@@ -23819,7 +23714,8 @@ var RubyAstVisitor = class {
23819
23714
  const { a, state } = this.op;
23820
23715
  const info = new FunctionInfo(name, node, this.caller(node), this.moduleInfo);
23821
23716
  a.functionInfos.set(node, info);
23822
- if (isBlockNode(node) || isDoBlockNode(node)) return;
23717
+ if (isBlockNode(node) || isDoBlockNode(node))
23718
+ return;
23823
23719
  const scopes = [];
23824
23720
  for (let i = this.scopes.length - 1; i >= 0; i--) {
23825
23721
  const s = this.scopes[i];
@@ -23830,39 +23726,46 @@ var RubyAstVisitor = class {
23830
23726
  name2 = name2.slice(2);
23831
23727
  i = 0;
23832
23728
  }
23833
- } else if (isSingletonClassNode(s)) name2 = `<<${fqNodeText(s.valueNode) ?? ""}`;
23834
- if (name2) scopes.push(name2);
23729
+ } else if (isSingletonClassNode(s))
23730
+ name2 = `<<${fqNodeText(s.valueNode) ?? ""}`;
23731
+ if (name2)
23732
+ scopes.push(name2);
23835
23733
  }
23836
23734
  let fqName = name;
23837
- if (isClassNode(node)) fqName = "<constructor>";
23838
- else if (isSingletonMethodNode(node)) fqName = `${fqNodeText(node.objectNode) ?? "?"}.${node.nameNode.text}`;
23839
- else fqName = node.nameNode.text;
23735
+ if (isClassNode(node))
23736
+ fqName = "<constructor>";
23737
+ else if (isSingletonMethodNode(node))
23738
+ fqName = `${fqNodeText(node.objectNode) ?? "?"}.${node.nameNode.text}`;
23739
+ else
23740
+ fqName = node.nameNode.text;
23840
23741
  state.fullyQualifiedNames.set(info, fqName = `${scopes.reverse().join("::")}#${fqName}`);
23841
23742
  if (!validateVulnerabilityID(fqName))
23842
23743
  assert8.fail(`Invalid fully qualified name for vulnerability matching: ${fqName}`);
23843
23744
  }
23844
23745
  };
23845
23746
  function fqNodeText(n12) {
23846
- if (isIdentifierNode(n12) || isConstantNode(n12) || isScopeResolutionNode(n12) || isSelfNode(n12)) return n12.text;
23747
+ if (isIdentifierNode(n12) || isConstantNode(n12) || isScopeResolutionNode(n12) || isSelfNode(n12))
23748
+ return n12.text;
23847
23749
  }
23848
23750
 
23849
- // ../ruby-analyzer/src/ruby-state.ts
23751
+ // ../ruby-analyzer/dist/ruby-state.js
23850
23752
  var RubyState = class {
23753
+ globalNatives;
23754
+ loadPath;
23755
+ constantsToNodes = /* @__PURE__ */ new Map();
23756
+ classInstantiations = new Array();
23757
+ fullyQualifiedNames = /* @__PURE__ */ new Map();
23851
23758
  constructor(globalNatives, loadPath) {
23852
23759
  this.globalNatives = globalNatives;
23853
23760
  this.loadPath = loadPath;
23854
23761
  }
23855
- // Maps class constants to the syntax nodes where they are defined.
23856
- // (Classes and modules can be defined and re-opened in multiple places, e.g. in different files.)
23857
- constantsToNodes = /* @__PURE__ */ new Map();
23858
- // Keeps track of instantiations of classes.
23859
- // Used to add call edges after the analysis is done.
23860
- classInstantiations = new Array();
23861
- fullyQualifiedNames = /* @__PURE__ */ new Map();
23862
23762
  };
23863
23763
 
23864
- // ../ruby-analyzer/src/ruby-analyzer.ts
23764
+ // ../ruby-analyzer/dist/ruby-analyzer.js
23865
23765
  var RubyAnalyzer = class {
23766
+ solver;
23767
+ state;
23768
+ op;
23866
23769
  constructor(solver, loadPath) {
23867
23770
  this.solver = solver;
23868
23771
  const constraintVarProducer = new ConstraintVarProducer();
@@ -23870,34 +23773,29 @@ var RubyAnalyzer = class {
23870
23773
  this.state = new RubyState(buildNatives(solver, tokenFactory, constraintVarProducer), loadPath);
23871
23774
  this.op = new Operations(solver, this.state, constraintVarProducer, tokenFactory);
23872
23775
  }
23873
- state;
23874
- op;
23875
23776
  async findFilesToAnalyze() {
23876
23777
  const { rootDir } = this.solver.globalState;
23877
23778
  const vendorDir = resolve2(rootDir, "vendor");
23878
- return (await findFiles(
23879
- rootDir,
23880
- async (file) => {
23881
- if (basename2(file) === "config.ru" || file.endsWith(".rb")) return true;
23882
- if (/\bbin\/[^./]+$/.test(file)) {
23883
- const head = Buffer.concat(await Array.fromAsync(createReadStream(file, { start: 0, end: 127 }))).toString(
23884
- "utf8"
23885
- );
23886
- return /^#!.*\bruby\b/.test(head);
23887
- }
23888
- return false;
23889
- },
23890
- (dir) => dir !== vendorDir
23891
- )).map((file) => [this.op.getContainingGem(dirname3(file), true), file]);
23779
+ return (await findFiles(rootDir, async (file) => {
23780
+ if (basename2(file) === "config.ru" || file.endsWith(".rb"))
23781
+ return true;
23782
+ if (/\bbin\/[^./]+$/.test(file)) {
23783
+ const head = Buffer.concat(await Array.fromAsync(createReadStream(file, { start: 0, end: 127 }))).toString("utf8");
23784
+ return /^#!.*\bruby\b/.test(head);
23785
+ }
23786
+ return false;
23787
+ }, (dir) => dir !== vendorDir)).map((file) => [this.op.getContainingGem(dirname3(file), true), file]);
23892
23788
  }
23893
23789
  async parse(filePath) {
23894
23790
  const tree = parser.parse(await readFile(filePath, "utf8"));
23895
23791
  if (tree.rootNode.isError) {
23896
23792
  if (/<%.*%>/s.test(tree.rootNode.text))
23897
23793
  logger.warn(`File '${filePath}' appears to be an ERB template. Skipping analysis.`);
23898
- else logger.error(`Failed to parse Ruby file '${filePath}'!`);
23794
+ else
23795
+ logger.error(`Failed to parse Ruby file '${filePath}'!`);
23899
23796
  return;
23900
- } else if (tree.rootNode.hasError) logger.warn(`Parsed Ruby file '${filePath}' with syntax errors!`);
23797
+ } else if (tree.rootNode.hasError)
23798
+ logger.warn(`Parsed Ruby file '${filePath}' with syntax errors!`);
23901
23799
  return tree;
23902
23800
  }
23903
23801
  visit(moduleInfo, tree) {
@@ -23913,7 +23811,9 @@ var RubyAnalyzer = class {
23913
23811
  patch() {
23914
23812
  const { functionInfos } = this.op.a;
23915
23813
  const calledFunctions = new Set(this.solver.callGraph.functionToFunction.values().flatMap((f) => f.values()));
23916
- for (const moduleInfo of this.op.a.moduleInfos.values()) if (moduleInfo.isEntry) calledFunctions.add(moduleInfo);
23814
+ for (const moduleInfo of this.op.a.moduleInfos.values())
23815
+ if (moduleInfo.isEntry)
23816
+ calledFunctions.add(moduleInfo);
23917
23817
  const patched = /* @__PURE__ */ new Set();
23918
23818
  for (const t15 of this.op.a.allTokens())
23919
23819
  if (t15 instanceof FunctionToken && t15.kind !== "method" && (isBlockNode(t15.fun) || isDoBlockNode(t15.fun))) {
@@ -23939,7 +23839,8 @@ var RubyAnalyzer = class {
23939
23839
  const vs = this.solver.globalState.options.vulnerabilities;
23940
23840
  assert9(vs?.length);
23941
23841
  const vulnTargets = new Map(vs.map((v) => [v, []]));
23942
- for (const [fun, fqn] of this.state.fullyQualifiedNames) vulnTargets.get(fqn)?.push(fun);
23842
+ for (const [fun, fqn] of this.state.fullyQualifiedNames)
23843
+ vulnTargets.get(fqn)?.push(fun);
23943
23844
  return vulnTargets;
23944
23845
  }
23945
23846
  };
@@ -23949,15 +23850,20 @@ function scopeAnalysis(tree) {
23949
23850
  analyzeScope(tree.rootNode);
23950
23851
  return bindings;
23951
23852
  function analyzeScope(node, scope = {}) {
23952
- if (!node) return;
23853
+ if (!node)
23854
+ return;
23953
23855
  if (isLambdaNode(node) || isBlockNode(node) || isDoBlockNode(node)) {
23954
23856
  scope = { ...scope };
23955
23857
  bindParameters(node.parametersNode, scope);
23956
23858
  } else if (isMethodNode(node) || isSingletonMethodNode(node) || isClassNode(node) || isSingletonClassNode(node) || isModuleNode(node)) {
23957
- if (isSingletonMethodNode(node)) analyzeScope(node.objectNode, scope);
23958
- else if (isSingletonClassNode(node)) analyzeScope(node.valueNode, scope);
23959
- else if (isClassNode(node)) analyzeScope(node.superclassNode, scope);
23960
- if ("nameNode" in node) analyzeScope(node.nameNode, scope);
23859
+ if (isSingletonMethodNode(node))
23860
+ analyzeScope(node.objectNode, scope);
23861
+ else if (isSingletonClassNode(node))
23862
+ analyzeScope(node.valueNode, scope);
23863
+ else if (isClassNode(node))
23864
+ analyzeScope(node.superclassNode, scope);
23865
+ if ("nameNode" in node)
23866
+ analyzeScope(node.nameNode, scope);
23961
23867
  const newScope = {};
23962
23868
  if ("parametersNode" in node) {
23963
23869
  bindParameters(node.parametersNode, newScope);
@@ -23970,7 +23876,8 @@ function scopeAnalysis(tree) {
23970
23876
  if (isIdentifierNode(node2))
23971
23877
  scope[node2.text] ??= node2;
23972
23878
  else if (isLeftAssignmentListNode(node2) || isRestAssignmentNode(node2) || isDestructuredLeftAssignmentNode(node2))
23973
- for (const child of node2.namedChildren) aux(child);
23879
+ for (const child of node2.namedChildren)
23880
+ aux(child);
23974
23881
  };
23975
23882
  aux(node.leftNode);
23976
23883
  } else if (isRescueNode(node) && node.variableNode) {
@@ -23993,34 +23900,37 @@ function scopeAnalysis(tree) {
23993
23900
  scope[node.nameNode.text] ??= node.nameNode;
23994
23901
  else if (isIdentifierNode(node)) {
23995
23902
  const dnode = scope[node.text];
23996
- if (dnode) bindings.set(node, dnode);
23903
+ if (dnode)
23904
+ bindings.set(node, dnode);
23997
23905
  }
23998
- for (const child of node.namedChildren) analyzeScope(child, scope);
23906
+ for (const child of node.namedChildren)
23907
+ analyzeScope(child, scope);
23999
23908
  }
24000
23909
  function bindParameters(parameters, newScope) {
24001
- if (!parameters) return;
23910
+ if (!parameters)
23911
+ return;
24002
23912
  for (const param of parameters.namedChildren) {
24003
23913
  let id;
24004
- if (isIdentifierNode(param)) id = param;
24005
- else if (isOptionalParameterNode(param)) id = param.nameNode;
24006
- else if (isKeywordParameterNode(param)) id = param.nameNode;
24007
- else if (isBlockParameterNode(param)) id = param.nameNode;
24008
- else if (isDestructuredParameterNode(param)) bindParameters(param, newScope);
24009
- if (id) newScope[id.text] = id;
23914
+ if (isIdentifierNode(param))
23915
+ id = param;
23916
+ else if (isOptionalParameterNode(param))
23917
+ id = param.nameNode;
23918
+ else if (isKeywordParameterNode(param))
23919
+ id = param.nameNode;
23920
+ else if (isBlockParameterNode(param))
23921
+ id = param.nameNode;
23922
+ else if (isDestructuredParameterNode(param))
23923
+ bindParameters(param, newScope);
23924
+ if (id)
23925
+ newScope[id.text] = id;
24010
23926
  }
24011
23927
  }
24012
23928
  }
24013
23929
 
24014
- // ../analysis-engine/src/solver.ts
23930
+ // ../analysis-engine/dist/solver.js
24015
23931
  import assert10 from "node:assert";
24016
23932
  var Solver = class {
24017
- constructor(globalState) {
24018
- this.globalState = globalState;
24019
- this.diagnostics = globalState.diagnostics;
24020
- }
24021
- /**
24022
- * Map from listener ID to listener key. Only used for checking hash collisions on listeners.
24023
- */
23933
+ globalState;
24024
23934
  listeners = /* @__PURE__ */ new Map();
24025
23935
  callGraph = new CallGraph();
24026
23936
  listenersProcessed = /* @__PURE__ */ new Map();
@@ -24028,19 +23938,17 @@ var Solver = class {
24028
23938
  diagnostics;
24029
23939
  nodesWithNewEdges = /* @__PURE__ */ new Set();
24030
23940
  postponedListenersProcessed = 0;
24031
- /**
24032
- * Adds a single token constraint.
24033
- */
23941
+ constructor(globalState) {
23942
+ this.globalState = globalState;
23943
+ this.diagnostics = globalState.diagnostics;
23944
+ }
24034
23945
  addTokenConstraint(t15, to) {
24035
- if (to === void 0) return;
23946
+ if (to === void 0)
23947
+ return;
24036
23948
  if (logger.isDebugEnabled())
24037
23949
  logger.debug(`Adding constraint ${t15} \u2208 ${to}`);
24038
23950
  this.addToken(t15, to);
24039
23951
  }
24040
- /**
24041
- * Adds a single token if not already present.
24042
- * Also enqueues notification of listeners and registers object properties and array entries from the constraint variable.
24043
- */
24044
23952
  addToken(t15, toRep) {
24045
23953
  const state = this.globalState;
24046
23954
  if (state.addToken(t15, toRep)) {
@@ -24050,80 +23958,69 @@ var Solver = class {
24050
23958
  }
24051
23959
  return false;
24052
23960
  }
24053
- /**
24054
- * Adds a set of tokens if not already present.
24055
- * Also adds to worklist and notifies listeners.
24056
- */
24057
23961
  addTokens(ts, to) {
24058
23962
  const state = this.globalState;
24059
23963
  state.vars.add(to);
24060
23964
  if (ts instanceof TokenInterface) {
24061
- if (state.addToken(ts, to)) this.tokenAdded(to, ts);
23965
+ if (state.addToken(ts, to))
23966
+ this.tokenAdded(to, ts);
24062
23967
  } else {
24063
23968
  let ws;
24064
- for (const t15 of state.addTokens(ts, to)) ws = this.tokenAdded(to, t15, ws);
23969
+ for (const t15 of state.addTokens(ts, to))
23970
+ ws = this.tokenAdded(to, t15, ws);
24065
23971
  }
24066
23972
  }
24067
23973
  tokenAdded(toRep, t15, ws) {
24068
23974
  ws ??= this.varsToUnprocessedTokens.get(toRep);
24069
23975
  ws = pushArraySingle(this.varsToUnprocessedTokens, toRep, t15, ws);
24070
23976
  this.diagnostics.unprocessedTokensSize++;
24071
- if (this.diagnostics.unprocessedTokensSize % 100 === 0) this.printDiagnostics();
23977
+ if (this.diagnostics.unprocessedTokensSize % 100 === 0)
23978
+ this.printDiagnostics();
24072
23979
  return ws;
24073
23980
  }
24074
- /**
24075
- * Adds a universally quantified constraint for a constraint variable.
24076
- * The listener key must uniquely determine the function (including its free variables).
24077
- */
24078
23981
  addForAllTokensConstraint(v, key, opts, listener) {
24079
- if (v === void 0) return;
23982
+ if (v === void 0)
23983
+ return;
24080
23984
  const lkey = { l: key, ...opts };
24081
23985
  if (logger.isDebugEnabled())
24082
- logger.debug(
24083
- `Adding universally quantified constraint to ${v}: [${t5(t6(lkey, { n: nodeLocationToString, l: (l) => this.listenerName(l) })).map(([k, v2]) => `${k}: ${v2}`).join(", ")}]}`
24084
- );
23986
+ logger.debug(`Adding universally quantified constraint to ${v}: [${t5(t6(lkey, { n: nodeLocationToString, l: (l) => this.listenerName(l) })).map(([k, v2]) => `${k}: ${v2}`).join(", ")}]}`);
24085
23987
  this.addForAllTokensConstraintPrivate(v, this.getListenerID(lkey), listener);
24086
23988
  }
24087
23989
  addForAllTokensConstraintPrivate(v, id, listener) {
24088
23990
  const m = mapGetMap(this.globalState.tokenListeners, v);
24089
23991
  if (!m.has(id)) {
24090
- for (const t15 of this.globalState.getTokens(v)) this.callTokenListener(id, listener, t15);
23992
+ for (const t15 of this.globalState.getTokens(v))
23993
+ this.callTokenListener(id, listener, t15);
24091
23994
  m.set(id, listener);
24092
23995
  this.globalState.vars.add(v);
24093
23996
  return true;
24094
23997
  }
24095
23998
  return false;
24096
23999
  }
24097
- /**
24098
- * Enqueues a call to a token listener if it hasn't been done before.
24099
- */
24100
24000
  callTokenListener(id, listener, t15, now = false) {
24101
24001
  const s = mapGetSet(this.listenersProcessed, id);
24102
24002
  if (setAdd(s, t15)) {
24103
- if (now) listener(t15);
24003
+ if (now)
24004
+ listener(t15);
24104
24005
  else {
24105
24006
  this.enqueueListenerCall([listener, t15]);
24106
24007
  this.diagnostics.tokenListenerNotifications++;
24107
24008
  }
24108
24009
  }
24109
24010
  }
24110
- /**
24111
- * Enqueues a listener call consisting of a listener and its argument(s).
24112
- */
24113
24011
  enqueueListenerCall(la) {
24114
24012
  this.globalState.postponedListenerCalls.push(la);
24115
24013
  }
24116
- /**
24117
- * Provides a unique'ish ID for the given ListenerKey.
24118
- */
24119
24014
  getListenerID(key) {
24120
24015
  let id = 0n;
24121
24016
  if (key.t) {
24122
24017
  assert10(key.t.hash !== void 0);
24123
24018
  id += BigInt(key.t.hash);
24124
24019
  }
24125
- if (key.n) id += BigInt(strHash(nodeLocationToString(key.n)));
24126
- if (key.s) id ^= BigInt(strHash(key.s));
24020
+ if (key.n)
24021
+ id += BigInt(strHash(nodeLocationToString(key.n)));
24022
+ if (key.s)
24023
+ id ^= BigInt(strHash(key.s));
24127
24024
  id = id << 16n | BigInt(key.l);
24128
24025
  this.checkListenerIDCollision(id, key);
24129
24026
  return id;
@@ -24134,14 +24031,14 @@ var Solver = class {
24134
24031
  if (x.l !== key.l || !nodeEq(x.n, key.n) || x.t !== key.t || x.s !== key.s) {
24135
24032
  throw new Error("Hash collision in getListenerID");
24136
24033
  }
24137
- } else this.listeners.set(id, key);
24034
+ } else
24035
+ this.listeners.set(id, key);
24138
24036
  }
24139
- /**
24140
- * Adds a subset constraint.
24141
- */
24142
24037
  addSubsetConstraint(from, to) {
24143
- if (from === void 0 || to === void 0) return;
24144
- if (logger.isDebugEnabled()) logger.debug(`Adding constraint ${from} \u2286 ${to}`);
24038
+ if (from === void 0 || to === void 0)
24039
+ return;
24040
+ if (logger.isDebugEnabled())
24041
+ logger.debug(`Adding constraint ${from} \u2286 ${to}`);
24145
24042
  this.addSubsetEdge(from, to);
24146
24043
  }
24147
24044
  addSubsetEdge(from, to) {
@@ -24156,9 +24053,7 @@ var Solver = class {
24156
24053
  const [size, ts] = state.getTokensSize(from);
24157
24054
  if (size > 0) {
24158
24055
  if (logger.isDebugEnabled())
24159
- logger.debug(
24160
- `Worklist size: ${this.diagnostics.unprocessedTokensSize}, propagating ${size} token${size === 1 ? "" : "s"} from ${from}`
24161
- );
24056
+ logger.debug(`Worklist size: ${this.diagnostics.unprocessedTokensSize}, propagating ${size} token${size === 1 ? "" : "s"} from ${from}`);
24162
24057
  this.addTokens(ts, to);
24163
24058
  this.incrementPropagations();
24164
24059
  }
@@ -24166,23 +24061,6 @@ var Solver = class {
24166
24061
  }
24167
24062
  }
24168
24063
  }
24169
- /**
24170
- * Adds an object property and notifies listeners.
24171
- addObjectProperty(objVar: CV, prop: string) {
24172
- const state = this.globalState;
24173
- const ps = mapGetSet(state.objectProperties, objVar);
24174
- if (!ps.has(prop)) {
24175
- if (logger.isDebugEnabled()) logger.debug(`Adding object property ${objVar}.${prop}`);
24176
- ps.add(prop);
24177
- const ts = state.objectPropertyListeners.get(objVar);
24178
- if (ts)
24179
- for (const listener of ts.values()) {
24180
- this.enqueueListenerCall([listener, prop]);
24181
- this.diagnostics.objectPropertiesListenerNotifications++;
24182
- }
24183
- }
24184
- }
24185
- */
24186
24064
  incrementPropagations() {
24187
24065
  this.diagnostics.propagations++;
24188
24066
  if (this.diagnostics.propagations % 100 === 0) {
@@ -24192,17 +24070,13 @@ var Solver = class {
24192
24070
  }
24193
24071
  printDiagnostics() {
24194
24072
  }
24195
- // eslint-disable-line @typescript-eslint/no-empty-function
24196
- /**
24197
- * Processes all items in the worklist until a fixpoint is reached.
24198
- * This notifies listeners and propagates tokens along subset edges.
24199
- */
24200
24073
  async propagate() {
24201
24074
  const timer = new Timer();
24202
24075
  const { globalState: state, diagnostics: d } = this;
24203
24076
  while (this.varsToUnprocessedTokens.size > 0 || this.nodesWithNewEdges.size > 0) {
24204
24077
  this.nodesWithNewEdges.clear();
24205
- for (const v of this.varsToUnprocessedTokens.keys()) this.processTokens(v);
24078
+ for (const v of this.varsToUnprocessedTokens.keys())
24079
+ this.processTokens(v);
24206
24080
  if (state.postponedListenerCalls.length > 0) {
24207
24081
  if (logger.isVerboseEnabled())
24208
24082
  logger.verbose(`Processing listener calls: ${state.postponedListenerCalls.length}`);
@@ -24221,31 +24095,31 @@ var Solver = class {
24221
24095
  }
24222
24096
  d.timings.propagation += timer.elapsed();
24223
24097
  }
24224
- /**
24225
- * Processes the items in the token worklist for the given constraint variable.
24226
- */
24227
24098
  processTokens(v) {
24228
24099
  const ts = this.varsToUnprocessedTokens.get(v);
24229
24100
  if (ts !== void 0) {
24230
24101
  this.varsToUnprocessedTokens.delete(v);
24231
24102
  const size = Array.isArray(ts) ? ts.length : 1;
24232
24103
  if (logger.isDebugEnabled())
24233
- logger.debug(
24234
- `Worklist size: ${this.diagnostics.unprocessedTokensSize}, propagating ${size} token${size === 1 ? "" : "s"} from ${v}`
24235
- );
24104
+ logger.debug(`Worklist size: ${this.diagnostics.unprocessedTokensSize}, propagating ${size} token${size === 1 ? "" : "s"} from ${v}`);
24236
24105
  this.diagnostics.unprocessedTokensSize -= size;
24237
24106
  const state = this.globalState;
24238
24107
  assert10(state.vars.has(v));
24239
24108
  const s = state.subsetEdges.get(v);
24240
24109
  if (s) {
24241
- for (const to of s) this.addTokens(Array.isArray(ts) ? ts : [ts], to);
24110
+ for (const to of s)
24111
+ this.addTokens(Array.isArray(ts) ? ts : [ts], to);
24242
24112
  this.incrementPropagations();
24243
24113
  }
24244
24114
  const tr = state.tokenListeners.get(v);
24245
24115
  if (tr)
24246
24116
  if (Array.isArray(ts))
24247
- for (const t15 of ts) for (const [id, listener] of tr) this.callTokenListener(id, listener, t15);
24248
- else for (const [id, listener] of tr) this.callTokenListener(id, listener, ts);
24117
+ for (const t15 of ts)
24118
+ for (const [id, listener] of tr)
24119
+ this.callTokenListener(id, listener, t15);
24120
+ else
24121
+ for (const [id, listener] of tr)
24122
+ this.callTokenListener(id, listener, ts);
24249
24123
  }
24250
24124
  }
24251
24125
  listenersProcessedByTokenListener() {
@@ -24258,7 +24132,7 @@ var Solver = class {
24258
24132
  }
24259
24133
  };
24260
24134
 
24261
- // ../ruby-analyzer/src/types/ruby-solver.ts
24135
+ // ../ruby-analyzer/dist/types/ruby-solver.js
24262
24136
  var RubySolver = class extends Solver {
24263
24137
  listenerName(l) {
24264
24138
  return TokenListener[l];
@@ -24269,11 +24143,11 @@ var RubySolver = class extends Solver {
24269
24143
  import assert12 from "node:assert";
24270
24144
  import { resolve as resolve3 } from "node:path";
24271
24145
 
24272
- // ../analysis-engine/src/global-state.ts
24146
+ // ../analysis-engine/dist/global-state.js
24273
24147
  import assert11 from "node:assert";
24274
24148
  import { join as join3, relative as relative2 } from "node:path";
24275
24149
 
24276
- // ../analysis-engine/src/diagnostics.ts
24150
+ // ../analysis-engine/dist/diagnostics.js
24277
24151
  import { inspect } from "node:util";
24278
24152
  var AnalysisDiagnostics = class {
24279
24153
  timedOut = false;
@@ -24284,37 +24158,25 @@ var AnalysisDiagnostics = class {
24284
24158
  listenerNotificationRounds = 0;
24285
24159
  objectPropertiesListenerNotifications = 0;
24286
24160
  timings = {
24287
- ...t7(
24288
- [
24289
- "listenerCall",
24290
- "preAnalysis",
24291
- "parsing",
24292
- "constraintSetup",
24293
- "propagation",
24294
- "vulnAnalysis",
24295
- "vulnPaths"
24296
- ],
24297
- () => 0n
24298
- ),
24161
+ ...t7([
24162
+ "listenerCall",
24163
+ "preAnalysis",
24164
+ "parsing",
24165
+ "constraintSetup",
24166
+ "propagation",
24167
+ "vulnAnalysis",
24168
+ "vulnPaths"
24169
+ ], () => 0n),
24299
24170
  [inspect.custom](_depth, options, f) {
24300
24171
  return f(t9(this, nanoToMs), options);
24301
24172
  }
24302
24173
  };
24303
24174
  };
24304
24175
 
24305
- // ../analysis-engine/src/global-state.ts
24176
+ // ../analysis-engine/dist/global-state.js
24306
24177
  var GlobalState = class _GlobalState {
24307
- // readonly objectProperties = new Map<CV, Set<string>>();
24308
- //
24309
- // objectPropertyListeners = new Map<CV, Map<ListenerID, (prop: string) => void>>();
24310
- constructor(rootDir, options) {
24311
- this.rootDir = rootDir;
24312
- this.options = options;
24313
- this.timeoutTimer = new Timer(options.timeout);
24314
- }
24315
- /**
24316
- * Map from absolute paths to ModuleInfo.
24317
- */
24178
+ rootDir;
24179
+ options;
24318
24180
  moduleInfos = /* @__PURE__ */ new Map();
24319
24181
  packageInfos = /* @__PURE__ */ new Set();
24320
24182
  _moduleWorklist = new Queue();
@@ -24322,7 +24184,6 @@ var GlobalState = class _GlobalState {
24322
24184
  functionInfos = new NodeMap();
24323
24185
  diagnostics = new AnalysisDiagnostics();
24324
24186
  warningsUnsupported = new NodeMap();
24325
- // TODO: Move these fields to the solver?
24326
24187
  vars = /* @__PURE__ */ new Set();
24327
24188
  tokens = /* @__PURE__ */ new Map();
24328
24189
  tokenListeners = /* @__PURE__ */ new Map();
@@ -24331,16 +24192,19 @@ var GlobalState = class _GlobalState {
24331
24192
  reverseSubsetEdges = /* @__PURE__ */ new Map();
24332
24193
  numberOfSubsetEdges = 0;
24333
24194
  static EMPTY_TOKENS_SIZE = [0, []];
24334
- /**
24335
- * Timeout timer.
24336
- */
24337
24195
  timeoutTimer;
24338
24196
  postponedListenerCalls = [];
24197
+ constructor(rootDir, options) {
24198
+ this.rootDir = rootDir;
24199
+ this.options = options;
24200
+ this.timeoutTimer = new Timer(options.timeout);
24201
+ }
24339
24202
  discoverFile(packageInfo, filePath, isEntry = false) {
24340
24203
  let moduleInfo = this.moduleInfos.get(filePath);
24341
24204
  if (moduleInfo) {
24342
24205
  assert11.strictEqual(packageInfo, moduleInfo.packageInfo);
24343
- if (isEntry) assert11(moduleInfo.isEntry);
24206
+ if (isEntry)
24207
+ assert11(moduleInfo.isEntry);
24344
24208
  return [moduleInfo, false];
24345
24209
  }
24346
24210
  moduleInfo = new ModuleInfo(relative2(join3(this.rootDir, packageInfo.dir), filePath), packageInfo, isEntry, true);
@@ -24356,70 +24220,58 @@ var GlobalState = class _GlobalState {
24356
24220
  if (setAdd(warnings, message) && logger.isWarnEnabled())
24357
24221
  logger.warn(`Unsupported: ${message} at ${nodeToString(node)}`);
24358
24222
  }
24359
- /**
24360
- * Returns the tokens in the solution for the given constraint variable
24361
- * (or empty if v is undefined).
24362
- */
24363
24223
  getTokens(v) {
24364
24224
  if (v) {
24365
24225
  const ts = this.tokens.get(v);
24366
24226
  if (ts) {
24367
- if (ts instanceof TokenInterface) return [ts];
24227
+ if (ts instanceof TokenInterface)
24228
+ return [ts];
24368
24229
  return ts;
24369
24230
  }
24370
24231
  }
24371
24232
  return [];
24372
24233
  }
24373
- /**
24374
- * Returns a generator over all tokens in the solution.
24375
- */
24376
24234
  *allTokens() {
24377
24235
  for (const ts of this.tokens.values()) {
24378
- if (ts instanceof TokenInterface) yield ts;
24379
- else yield* ts;
24236
+ if (ts instanceof TokenInterface)
24237
+ yield ts;
24238
+ else
24239
+ yield* ts;
24380
24240
  }
24381
24241
  }
24382
- /**
24383
- * Returns the number of tokens in the solution for the given constraint variable, and the tokens.
24384
- */
24385
24242
  getTokensSize(v) {
24386
24243
  if (v) {
24387
24244
  const ts = this.tokens.get(v);
24388
24245
  if (ts) {
24389
- if (ts instanceof TokenInterface) return [1, [ts]];
24246
+ if (ts instanceof TokenInterface)
24247
+ return [1, [ts]];
24390
24248
  return [ts.size, ts];
24391
24249
  }
24392
24250
  }
24393
24251
  return _GlobalState.EMPTY_TOKENS_SIZE;
24394
24252
  }
24395
- /**
24396
- * Checks whether a constraint variable has a token.
24397
- */
24398
24253
  hasToken(v, t15) {
24399
24254
  const ts = this.tokens.get(v);
24400
- if (!ts) return false;
24401
- else if (ts instanceof TokenInterface) return ts === t15;
24402
- else return ts.has(t15);
24403
- }
24404
- /**
24405
- * Adds the given token to the solution for the given constraint variable.
24406
- * @return true if not already there, false if already there
24407
- */
24255
+ if (!ts)
24256
+ return false;
24257
+ else if (ts instanceof TokenInterface)
24258
+ return ts === t15;
24259
+ else
24260
+ return ts.has(t15);
24261
+ }
24408
24262
  addToken(t15, v) {
24409
24263
  const ts = this.tokens.get(v);
24410
- if (!ts) this.tokens.set(v, t15);
24264
+ if (!ts)
24265
+ this.tokens.set(v, t15);
24411
24266
  else if (ts instanceof TokenInterface) {
24412
- if (ts === t15) return false;
24267
+ if (ts === t15)
24268
+ return false;
24413
24269
  this.tokens.set(v, /* @__PURE__ */ new Set([ts, t15]));
24414
- } else if (!setAdd(ts, t15)) return false;
24270
+ } else if (!setAdd(ts, t15))
24271
+ return false;
24415
24272
  this.numberOfTokens++;
24416
24273
  return true;
24417
24274
  }
24418
- /**
24419
- * Adds the given tokens to the solution for the given constraint variable.
24420
- * It is assumed that the given set does not contain any duplicates.
24421
- * @return the tokens that have been added, excluding those already there
24422
- */
24423
24275
  addTokens(ts, v) {
24424
24276
  const added = [];
24425
24277
  let vs = this.tokens.get(v);
@@ -24435,49 +24287,46 @@ var GlobalState = class _GlobalState {
24435
24287
  this.tokens.set(v, vs);
24436
24288
  add = true;
24437
24289
  }
24438
- } else add = setAdd(vs, t15);
24439
- if (add) added.push(t15);
24290
+ } else
24291
+ add = setAdd(vs, t15);
24292
+ if (add)
24293
+ added.push(t15);
24440
24294
  }
24441
24295
  this.numberOfTokens += added.length;
24442
24296
  return added;
24443
24297
  }
24444
24298
  };
24445
24299
 
24446
- // ../analysis-engine/src/vulnerabilities.ts
24300
+ // ../analysis-engine/dist/vulnerabilities.js
24447
24301
  function analyzeVulnerabilities(d, callGraph, targets) {
24448
24302
  const timer = new Timer();
24449
- const parents = callGraph.reachableFunctions(
24450
- callGraph.functionToFunction.keys().filter((f) => f.isEntry).toArray()
24451
- );
24303
+ const parents = callGraph.reachableFunctions(callGraph.functionToFunction.keys().filter((f) => f.isEntry).toArray());
24452
24304
  d.timings.vulnAnalysis = timer.elapsed();
24453
24305
  timer.reset();
24454
- const results = Object.fromEntries(
24455
- targets.entries().map(([vuln, funcs]) => {
24456
- if (!funcs.length) return [vuln, { reachable: false, reason: "Function not found" }];
24457
- const reachableFuncs = funcs.filter((f) => parents.has(f));
24458
- if (!reachableFuncs.length)
24459
- return [vuln, { reachable: false, reason: "Function not reachable from application code" }];
24460
- return [
24461
- vuln,
24462
- {
24463
- reachable: true,
24464
- // TODO: More sophisticated call path generation
24465
- // TODO: Nodes should correspond to calls, not to functions
24466
- stacks: reachableFuncs.map((f) => {
24467
- const stack = [];
24468
- for (; f; f = parents.get(f))
24469
- stack.push({
24470
- package: f.packageInfo.toString(),
24471
- caller: f,
24472
- sourceLocation: f.loc,
24473
- confidence: 1
24474
- });
24475
- return stack.reverse();
24476
- })
24477
- }
24478
- ];
24479
- })
24480
- );
24306
+ const results = Object.fromEntries(targets.entries().map(([vuln, funcs]) => {
24307
+ if (!funcs.length)
24308
+ return [vuln, { reachable: false, reason: "Function not found" }];
24309
+ const reachableFuncs = funcs.filter((f) => parents.has(f));
24310
+ if (!reachableFuncs.length)
24311
+ return [vuln, { reachable: false, reason: "Function not reachable from application code" }];
24312
+ return [
24313
+ vuln,
24314
+ {
24315
+ reachable: true,
24316
+ stacks: reachableFuncs.map((f) => {
24317
+ const stack = [];
24318
+ for (; f; f = parents.get(f))
24319
+ stack.push({
24320
+ package: f.packageInfo.toString(),
24321
+ caller: f,
24322
+ sourceLocation: f.loc,
24323
+ confidence: 1
24324
+ });
24325
+ return stack.reverse();
24326
+ })
24327
+ }
24328
+ ];
24329
+ }));
24481
24330
  d.timings.vulnPaths += timer.elapsed();
24482
24331
  return results;
24483
24332
  }
@@ -24619,7 +24468,7 @@ ${inspect2(globalState.diagnostics, { depth: Infinity })}`);
24619
24468
  import assert14 from "node:assert";
24620
24469
  import fs3 from "node:fs/promises";
24621
24470
 
24622
- // ../utils/src/graph.ts
24471
+ // ../utils/dist/graph.js
24623
24472
  function transitiveClosure(adj, ...initial) {
24624
24473
  const result = new Set(initial);
24625
24474
  while (initial.length) {