parseman 0.61.5 → 0.61.6

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.
@@ -4072,7 +4072,7 @@ function regex(pattern, flags = "") {
4072
4072
  }
4073
4073
 
4074
4074
  // src/version.ts
4075
- var PARSEMAN_VERSION = "0.61.5";
4075
+ var PARSEMAN_VERSION = "0.61.6";
4076
4076
 
4077
4077
  // src/table/lex-body.ts
4078
4078
  function buildLexBodyRecognizer(spec, constants) {
package/dist/cli/index.js CHANGED
@@ -5708,7 +5708,7 @@ function regex(pattern, flags = "") {
5708
5708
  }
5709
5709
 
5710
5710
  // src/version.ts
5711
- var PARSEMAN_VERSION = "0.61.5";
5711
+ var PARSEMAN_VERSION = "0.61.6";
5712
5712
 
5713
5713
  // src/table/lex-body.ts
5714
5714
  function buildLexBodyRecognizer(spec, constants) {
package/dist/index.js CHANGED
@@ -5661,7 +5661,7 @@ function sourceLeaf(root, fn) {
5661
5661
  }
5662
5662
 
5663
5663
  // src/version.ts
5664
- var PARSEMAN_VERSION = "0.61.5";
5664
+ var PARSEMAN_VERSION = "0.61.6";
5665
5665
 
5666
5666
  // src/table/lex-body.ts
5667
5667
  function buildLexBodyRecognizer(spec, constants) {
@@ -19833,21 +19833,70 @@ function runDuplicationDiagnosticRules(ruleMap, opt) {
19833
19833
  var LOOP = 8;
19834
19834
  var ROUNDS = 60;
19835
19835
  var CAP = 1e12;
19836
+ var CROSSING_WEIGHT = 4;
19837
+ var TAKEN = -1;
19836
19838
  function selectHotSites(code, entries, siteBytes, budget, profile) {
19837
19839
  const selected = /* @__PURE__ */ new Set();
19838
19840
  if (budget <= 0) return selected;
19839
- const weight = profile === void 0 ? staticWeights(code, entries) : void 0;
19840
- const w = (ip) => (weight !== void 0 ? weight.get(ip) : profile[ip]) ?? 0;
19841
- const ranked = [...siteBytes.keys()].sort((a, b) => w(b) / siteBytes.get(b) - w(a) / siteBytes.get(a) || a - b);
19842
19841
  let spent = 0;
19843
- for (const ip of ranked) {
19844
- if (w(ip) === 0) break;
19842
+ for (const ip of profile === void 0 ? staticRanking(code, entries, siteBytes) : connectedRanking(code, siteBytes, profile)) {
19845
19843
  spent += siteBytes.get(ip);
19846
19844
  if (spent > budget) break;
19847
19845
  selected.add(ip);
19848
19846
  }
19849
19847
  return selected;
19850
19848
  }
19849
+ function edgesAsLowered(code, siteBytes, ip, out) {
19850
+ out.length = 0;
19851
+ if (code[ip] !== OP_CONT) childSlots(code, ip, out);
19852
+ else if (siteBytes.has(ip)) out.push(code[ip + 1], code[ip + 3]);
19853
+ else out.push(code[ip + 2]);
19854
+ for (let i = 0; i < out.length; i++) {
19855
+ let row = out[i];
19856
+ for (; ; ) {
19857
+ const op = code[row];
19858
+ if (op === OP_GAPGATE || op === OP_SEED) row = code[row + 1];
19859
+ else if (op === OP_CONT && !siteBytes.has(row)) row = code[row + 2];
19860
+ else break;
19861
+ }
19862
+ out[i] = row;
19863
+ }
19864
+ }
19865
+ function staticRanking(code, entries, siteBytes) {
19866
+ const weight = staticWeights(code, entries, siteBytes);
19867
+ const w = (ip) => weight.get(ip) ?? 0;
19868
+ return [...siteBytes.keys()].filter((ip) => w(ip) > 0).sort((a, b) => w(b) / siteBytes.get(b) - w(a) / siteBytes.get(a) || a - b);
19869
+ }
19870
+ function* connectedRanking(code, siteBytes, calls) {
19871
+ const ran = [...siteBytes.keys()].filter((ip) => calls[ip] > 0).sort((a, b) => a - b);
19872
+ const slot = new Map(ran.map((ip, i) => [ip, i]));
19873
+ const bytes2 = ran.map((ip) => siteBytes.get(ip));
19874
+ const worth = ran.map((ip) => calls[ip]);
19875
+ const score = worth.map((value, i) => value / bytes2[i]);
19876
+ const crossings = ran.map(() => []);
19877
+ const kids = [];
19878
+ ran.forEach((ip, from) => {
19879
+ edgesAsLowered(code, siteBytes, ip, kids);
19880
+ for (const callee of kids) {
19881
+ const to = slot.get(callee);
19882
+ if (to === void 0) continue;
19883
+ const gain = CROSSING_WEIGHT * calls[callee];
19884
+ crossings[from].push([to, gain]);
19885
+ crossings[to].push([from, gain]);
19886
+ }
19887
+ });
19888
+ for (let left = ran.length; left > 0; left--) {
19889
+ let best = 0;
19890
+ for (let i = 1; i < score.length; i++) if (score[i] > score[best]) best = i;
19891
+ score[best] = TAKEN;
19892
+ yield ran[best];
19893
+ for (const [neighbour, gain] of crossings[best]) {
19894
+ if (score[neighbour] === TAKEN) continue;
19895
+ worth[neighbour] = worth[neighbour] + gain;
19896
+ score[neighbour] = worth[neighbour] / bytes2[neighbour];
19897
+ }
19898
+ }
19899
+ }
19851
19900
  function fitHotSites(code, entries, siteBytes, fixed, ceiling, sourceBytes, profile) {
19852
19901
  const ranked = [...selectHotSites(code, entries, siteBytes, ceiling - fixed, profile)];
19853
19902
  for (; ranked.length > 0; ranked.pop()) {
@@ -19857,25 +19906,17 @@ function fitHotSites(code, entries, siteBytes, fixed, ceiling, sourceBytes, prof
19857
19906
  }
19858
19907
  return void 0;
19859
19908
  }
19860
- function staticWeights(code, entries) {
19909
+ function staticWeights(code, entries, siteBytes) {
19861
19910
  let weight = /* @__PURE__ */ new Map();
19862
19911
  const kids = [];
19863
19912
  for (let round = 0; round < ROUNDS; round++) {
19864
19913
  const next = /* @__PURE__ */ new Map();
19865
19914
  for (const ip of entries) next.set(ip, 1);
19866
19915
  for (const [ip, w] of weight) {
19867
- kids.length = 0;
19868
- childSlots(code, ip, kids);
19916
+ edgesAsLowered(code, siteBytes, ip, kids);
19869
19917
  const op = code[ip];
19870
- if (op === OP_CONT && continuationGate(code, code[ip + 3]) !== void 0) {
19871
- kids.length = 0;
19872
- kids.push(code[ip + 1], code[ip + 3]);
19873
- }
19874
19918
  const scale = op === OP_REP || op === OP_REPV ? LOOP : op === OP_CHOICE || op === OP_DISPATCH ? 1 / Math.max(1, kids.length) : 1;
19875
- for (const k of kids) {
19876
- const kid = code[k] === OP_GAPGATE ? code[k + 1] : k;
19877
- next.set(kid, Math.min(CAP, (next.get(kid) ?? 0) + w * scale));
19878
- }
19919
+ for (const kid of kids) next.set(kid, Math.min(CAP, (next.get(kid) ?? 0) + w * scale));
19879
19920
  }
19880
19921
  weight = next;
19881
19922
  }