From 9d1558c1f923677d317751136929adb84f22234a Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 13:54:52 +0000 Subject: [PATCH 01/13] Plan: optimize linear recurrence loop access Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/4e0ce258-ef41-4a6f-be38-ffa472d9e8b4 Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- source_.jar | Bin 382864 -> 382864 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/source_.jar b/source_.jar index 6390be5cc12fe42830b3ec1d6f24f6b875311493..07988c46b1bf18264d7de52c4013627a5462de99 100644 GIT binary patch delta 13734 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 delta 13734 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 wH^}lrVCr5otcL6%HJEM Date: Sun, 12 Apr 2026 13:55:23 +0000 Subject: [PATCH 02/13] Implement rolling linear recurrence evaluation Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/4e0ce258-ef41-4a6f-be38-ffa472d9e8b4 Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- .../formula/LinearRecurrenceFormula.java | 61 +++++++++++++++++-- 1 file changed, 56 insertions(+), 5 deletions(-) diff --git a/src/main/java/cod/range/formula/LinearRecurrenceFormula.java b/src/main/java/cod/range/formula/LinearRecurrenceFormula.java index d0bc02b..770af55 100644 --- a/src/main/java/cod/range/formula/LinearRecurrenceFormula.java +++ b/src/main/java/cod/range/formula/LinearRecurrenceFormula.java @@ -14,6 +14,8 @@ public class LinearRecurrenceFormula { private final boolean hasConstantTerm; private final LinearRecurrenceFormula newerFormula; private final LinearRecurrenceFormula olderFormula; + private transient long rollingIndex = Long.MIN_VALUE; + private transient AutoStackingNumber[] rollingState = null; private static final AutoStackingNumber ZERO = AutoStackingNumber.fromLong(0L); private static final AutoStackingNumber ONE = AutoStackingNumber.fromLong(1L); @@ -94,10 +96,35 @@ public Object evaluate(long index) { return null; } + if (rollingState != null && index == rollingIndex) { + return rollingState[0]; + } + + if (rollingState != null && index == rollingIndex + 1L) { + advanceRollingState(); + rollingIndex = index; + return rollingState[0]; + } + long lastSeedIndex = recurrenceStart - 1L; long steps = index - lastSeedIndex; int dim = hasConstantTerm ? order + 1 : order; + AutoStackingNumber[][] transition = buildTransition(dim); + AutoStackingNumber[] state = buildBaseState(dim); + + AutoStackingNumber[][] power = matrixPow(transition, steps); + AutoStackingNumber[] result = multiply(power, state); + rollingState = copyState(result); + rollingIndex = index; + return result[0]; + } + + private boolean isComposite() { + return newerFormula != null || olderFormula != null; + } + + private AutoStackingNumber[][] buildTransition(int dim) { AutoStackingNumber[][] transition = new AutoStackingNumber[dim][dim]; for (int i = 0; i < dim; i++) { for (int j = 0; j < dim; j++) { @@ -118,6 +145,10 @@ public Object evaluate(long index) { transition[last][last] = ONE; } + return transition; + } + + private AutoStackingNumber[] buildBaseState(int dim) { AutoStackingNumber[] state = new AutoStackingNumber[dim]; for (int j = 0; j < order; j++) { state[j] = seedValues[order - 1 - j]; @@ -125,14 +156,34 @@ public Object evaluate(long index) { if (hasConstantTerm) { state[dim - 1] = ONE; } + return state; + } - AutoStackingNumber[][] power = matrixPow(transition, steps); - AutoStackingNumber[] result = multiply(power, state); - return result[0]; + private AutoStackingNumber[] copyState(AutoStackingNumber[] state) { + AutoStackingNumber[] out = new AutoStackingNumber[state.length]; + for (int i = 0; i < state.length; i++) { + out[i] = state[i]; + } + return out; } - private boolean isComposite() { - return newerFormula != null || olderFormula != null; + private void advanceRollingState() { + AutoStackingNumber next = hasConstantTerm ? constantTerm : ZERO; + for (int lag = 1; lag <= order; lag++) { + AutoStackingNumber coeff = coefficientsByLag[lag - 1]; + if (coeff != null && !coeff.isZero()) { + next = next.add(coeff.multiply(rollingState[lag - 1])); + } + } + + for (int i = order - 1; i >= 1; i--) { + rollingState[i] = rollingState[i - 1]; + } + rollingState[0] = next; + + if (hasConstantTerm) { + rollingState[rollingState.length - 1] = ONE; + } } private AutoStackingNumber[][] matrixPow(AutoStackingNumber[][] base, long exp) { From f8d9ed94357276a6e0a33740e49b5d61a95e4d33 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 13:57:09 +0000 Subject: [PATCH 03/13] Address validation feedback for recurrence optimization Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/4e0ce258-ef41-4a6f-be38-ffa472d9e8b4 Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- source_.jar | Bin 382864 -> 383151 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/source_.jar b/source_.jar index 07988c46b1bf18264d7de52c4013627a5462de99..ce781a18ccc2fdba400152a2785861bb350a82bc 100644 GIT binary patch delta 4944 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 Rm&^GnxrA5c7ztOcSh delta 4872 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 From c4e934a315af60269231b42e665d711e1c0a1bf2 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 13:57:36 +0000 Subject: [PATCH 04/13] Refine recurrence rolling cache safety Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/4e0ce258-ef41-4a6f-be38-ffa472d9e8b4 Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- source_.jar | Bin 383151 -> 383183 bytes .../formula/LinearRecurrenceFormula.java | 17 ++++++++--------- 2 files changed, 8 insertions(+), 9 deletions(-) diff --git a/source_.jar b/source_.jar index ce781a18ccc2fdba400152a2785861bb350a82bc..8ebd30c8cfa312a98da4d0382fc2646dfe1529ba 100644 GIT binary patch delta 5105 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 z SSsy0KLLUJ!>H$Z9vim>C(*+s; delta 5071 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 start && index <= end; } - public Object evaluate(long index) { + public synchronized Object evaluate(long index) { if (isComposite()) { if (newerFormula != null && newerFormula.contains(index)) { return newerFormula.evaluate(index); @@ -160,11 +161,7 @@ private AutoStackingNumber[] buildBaseState(int dim) { } private AutoStackingNumber[] copyState(AutoStackingNumber[] state) { - AutoStackingNumber[] out = new AutoStackingNumber[state.length]; - for (int i = 0; i < state.length; i++) { - out[i] = state[i]; - } - return out; + return Arrays.copyOf(state, state.length); } private void advanceRollingState() { @@ -176,14 +173,16 @@ private void advanceRollingState() { } } + AutoStackingNumber[] nextState = Arrays.copyOf(rollingState, rollingState.length); for (int i = order - 1; i >= 1; i--) { - rollingState[i] = rollingState[i - 1]; + nextState[i] = rollingState[i - 1]; } - rollingState[0] = next; + nextState[0] = next; if (hasConstantTerm) { - rollingState[rollingState.length - 1] = ONE; + nextState[nextState.length - 1] = ONE; } + rollingState = nextState; } private AutoStackingNumber[][] matrixPow(AutoStackingNumber[][] base, long exp) { From 72d1c948cb0f6cd20693b829b0e1ceaf0ca50f66 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 13:57:46 +0000 Subject: [PATCH 05/13] Restore source_jar artifact to branch baseline Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/4e0ce258-ef41-4a6f-be38-ffa472d9e8b4 Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- source_.jar | Bin 383183 -> 382864 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/source_.jar b/source_.jar index 8ebd30c8cfa312a98da4d0382fc2646dfe1529ba..6390be5cc12fe42830b3ec1d6f24f6b875311493 100644 GIT binary patch delta 15639 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 Ee{?V=TL1t6 delta 15919 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 T?!0zFEAOx-ax+)3p!WX&Yl6s6 From ff37af461f87863b4a1a92b2aa97157dc41a08f8 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 13:59:36 +0000 Subject: [PATCH 06/13] Finalize linear recurrence rolling-state optimization Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/4e0ce258-ef41-4a6f-be38-ffa472d9e8b4 Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- .../formula/LinearRecurrenceFormula.java | 39 ++++++++++++------- 1 file changed, 25 insertions(+), 14 deletions(-) diff --git a/src/main/java/cod/range/formula/LinearRecurrenceFormula.java b/src/main/java/cod/range/formula/LinearRecurrenceFormula.java index df33c2c..cf76ee3 100644 --- a/src/main/java/cod/range/formula/LinearRecurrenceFormula.java +++ b/src/main/java/cod/range/formula/LinearRecurrenceFormula.java @@ -15,6 +15,7 @@ public class LinearRecurrenceFormula { private final boolean hasConstantTerm; private final LinearRecurrenceFormula newerFormula; private final LinearRecurrenceFormula olderFormula; + private final Object rollingStateLock = new Object(); private transient long rollingIndex = Long.MIN_VALUE; private transient AutoStackingNumber[] rollingState = null; private static final AutoStackingNumber ZERO = AutoStackingNumber.fromLong(0L); @@ -40,6 +41,7 @@ public LinearRecurrenceFormula( this.hasConstantTerm = !this.constantTerm.isZero(); this.newerFormula = null; this.olderFormula = null; + resetRollingState(); } private LinearRecurrenceFormula(long start, long end, @@ -56,6 +58,7 @@ private LinearRecurrenceFormula(long start, long end, this.hasConstantTerm = false; this.newerFormula = newerFormula; this.olderFormula = olderFormula; + resetRollingState(); } public static LinearRecurrenceFormula compose(LinearRecurrenceFormula newerFormula, LinearRecurrenceFormula olderFormula) { @@ -74,7 +77,7 @@ public boolean contains(long index) { return index >= start && index <= end; } - public synchronized Object evaluate(long index) { + public Object evaluate(long index) { if (isComposite()) { if (newerFormula != null && newerFormula.contains(index)) { return newerFormula.evaluate(index); @@ -97,14 +100,15 @@ public synchronized Object evaluate(long index) { return null; } - if (rollingState != null && index == rollingIndex) { - return rollingState[0]; - } - - if (rollingState != null && index == rollingIndex + 1L) { - advanceRollingState(); - rollingIndex = index; - return rollingState[0]; + synchronized (rollingStateLock) { + if (rollingState != null && index == rollingIndex) { + return rollingState[0]; + } + if (rollingState != null && index == rollingIndex + 1L) { + advanceRollingState(); + rollingIndex = index; + return rollingState[0]; + } } long lastSeedIndex = recurrenceStart - 1L; @@ -116,8 +120,10 @@ public synchronized Object evaluate(long index) { AutoStackingNumber[][] power = matrixPow(transition, steps); AutoStackingNumber[] result = multiply(power, state); - rollingState = copyState(result); - rollingIndex = index; + synchronized (rollingStateLock) { + rollingState = copyState(result); + rollingIndex = index; + } return result[0]; } @@ -173,11 +179,11 @@ private void advanceRollingState() { } } - AutoStackingNumber[] nextState = Arrays.copyOf(rollingState, rollingState.length); - for (int i = order - 1; i >= 1; i--) { + AutoStackingNumber[] nextState = new AutoStackingNumber[rollingState.length]; + nextState[0] = next; + for (int i = 1; i < order; i++) { nextState[i] = rollingState[i - 1]; } - nextState[0] = next; if (hasConstantTerm) { nextState[nextState.length - 1] = ONE; @@ -185,6 +191,11 @@ private void advanceRollingState() { rollingState = nextState; } + private void resetRollingState() { + rollingIndex = Long.MIN_VALUE; + rollingState = null; + } + private AutoStackingNumber[][] matrixPow(AutoStackingNumber[][] base, long exp) { int dim = base.length; AutoStackingNumber[][] result = identity(dim); From 501d55b3275689d9e1c42e9559db87f3fea89caa Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 14:00:58 +0000 Subject: [PATCH 07/13] Simplify recurrence cache synchronization Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/4e0ce258-ef41-4a6f-be38-ffa472d9e8b4 Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- src/main/java/cod/range/formula/LinearRecurrenceFormula.java | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/src/main/java/cod/range/formula/LinearRecurrenceFormula.java b/src/main/java/cod/range/formula/LinearRecurrenceFormula.java index cf76ee3..bfe2185 100644 --- a/src/main/java/cod/range/formula/LinearRecurrenceFormula.java +++ b/src/main/java/cod/range/formula/LinearRecurrenceFormula.java @@ -15,7 +15,6 @@ public class LinearRecurrenceFormula { private final boolean hasConstantTerm; private final LinearRecurrenceFormula newerFormula; private final LinearRecurrenceFormula olderFormula; - private final Object rollingStateLock = new Object(); private transient long rollingIndex = Long.MIN_VALUE; private transient AutoStackingNumber[] rollingState = null; private static final AutoStackingNumber ZERO = AutoStackingNumber.fromLong(0L); @@ -100,7 +99,7 @@ public Object evaluate(long index) { return null; } - synchronized (rollingStateLock) { + synchronized (this) { if (rollingState != null && index == rollingIndex) { return rollingState[0]; } @@ -120,7 +119,7 @@ public Object evaluate(long index) { AutoStackingNumber[][] power = matrixPow(transition, steps); AutoStackingNumber[] result = multiply(power, state); - synchronized (rollingStateLock) { + synchronized (this) { rollingState = copyState(result); rollingIndex = index; } From 191ca14230d37208a23dbc8d7f0f83aa9b4d49a9 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 14:14:32 +0000 Subject: [PATCH 08/13] Plan vector recurrence optimization support Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/6399c570-b95d-4d37-a5ef-4f2b988df11d Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- source_.jar | Bin 382864 -> 383203 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/source_.jar b/source_.jar index 6390be5cc12fe42830b3ec1d6f24f6b875311493..d8e3af8b7db6ed7ce04aec0ca834716b805cf610 100644 GIT binary patch delta 15938 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 O-D6GU*R5tj?f(J&F4c1Y delta 16046 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 Vv5q#AnP|yvWT$TNH*7jZ{|6e-=|BJg From 0dd3afc3d50d569c67757f5b750acd13636332cf Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 14:16:18 +0000 Subject: [PATCH 09/13] Implement vector recurrence core integration Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/6399c570-b95d-4d37-a5ef-4f2b988df11d Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- .../handler/LoopOptimizationHandler.java | 274 ++++++++++++++++++ .../interpreter/handler/PatternHandler.java | 141 ++++++++- src/main/java/cod/range/NaturalArray.java | 68 +++++ .../formula/VectorRecurrenceFormula.java | 260 +++++++++++++++++ 4 files changed, 742 insertions(+), 1 deletion(-) create mode 100644 src/main/java/cod/range/formula/VectorRecurrenceFormula.java diff --git a/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java b/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java index 0691603..447d111 100644 --- a/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java +++ b/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java @@ -22,6 +22,7 @@ public class LoopOptimizationHandler { private static final int LAZY_THRESHOLD = 10; private static final int MAX_SUPPORTED_LAG = 64; + private static final int MAX_VECTOR_SEQUENCES = 64; private final InterpreterVisitor dispatcher; private final TypeHandler typeSystem; @@ -218,6 +219,17 @@ public Object tryOptimizedExecution(For node, int loopId) { } } + List vectorRecurrencePatterns = extractVectorLinearRecurrencePatterns(node); + if (!vectorRecurrencePatterns.isEmpty()) { + try { + Object result = patternHandler.applyPatterns(node, vectorRecurrencePatterns); + ArrayTracker.markLoopOptimized(loopId); + return result; + } catch (Exception e) { + DebugSystem.debug("OPTIMIZER", "Vector recurrence pattern failed: " + e.getMessage()); + } + } + List multiArrayPatterns = extractMultiArraySequencePatterns(node); if (!multiArrayPatterns.isEmpty()) { try { @@ -282,6 +294,154 @@ public Object tryOptimizedExecution(For node, int loopId) { return null; } + public List extractVectorLinearRecurrencePatterns(For node) { + List results = new ArrayList(); + if (node == null || node.body == null || node.body.statements == null) { + return results; + } + + List assignments = collectVectorAssignments(node); + if (assignments.size() < 2 || assignments.size() > MAX_VECTOR_SEQUENCES) { + return results; + } + + List orderedTargets = new ArrayList(); + List targetExprs = new ArrayList(); + List targetArrays = new ArrayList(); + Map targetIndexByName = new LinkedHashMap(); + + for (Assignment assignment : assignments) { + IndexAccess leftAccess = (IndexAccess) assignment.left; + Identifier targetId = (Identifier) leftAccess.array; + String targetName = targetId.name; + if (targetIndexByName.containsKey(targetName)) { + return new ArrayList(); + } + Object resolved = dispatcher.dispatch(targetId); + resolved = typeSystem.unwrap(resolved); + if (!(resolved instanceof NaturalArray)) { + return new ArrayList(); + } + orderedTargets.add(targetName); + targetExprs.add(targetId); + targetArrays.add((NaturalArray) resolved); + targetIndexByName.put(targetName, targetIndexByName.size()); + } + + long expectedSize = targetArrays.get(0).size(); + for (int i = 1; i < targetArrays.size(); i++) { + if (targetArrays.get(i).size() != expectedSize) { + return new ArrayList(); + } + } + + int dimension = assignments.size(); + AutoStackingNumber[][][] coeffByLag = new AutoStackingNumber[dimension][MAX_SUPPORTED_LAG + 1][dimension]; + AutoStackingNumber[] constants = new AutoStackingNumber[dimension]; + for (int row = 0; row < dimension; row++) { + constants[row] = AutoStackingNumber.fromLong(0L); + for (int lag = 0; lag <= MAX_SUPPORTED_LAG; lag++) { + for (int col = 0; col < dimension; col++) { + coeffByLag[row][lag][col] = AutoStackingNumber.fromLong(0L); + } + } + } + + int maxLag = 0; + for (int row = 0; row < assignments.size(); row++) { + Assignment assign = assignments.get(row); + AutoStackingNumber[] constantRef = new AutoStackingNumber[]{AutoStackingNumber.fromLong(0L)}; + if (!collectVectorLinearTerms( + assign.right, + targetIndexByName, + node.iterator, + coeffByLag[row], + constantRef, + AutoStackingNumber.fromLong(1L))) { + return new ArrayList(); + } + constants[row] = constantRef[0]; + } + + for (int row = 0; row < dimension; row++) { + boolean hasDependency = false; + for (int lag = 1; lag <= MAX_SUPPORTED_LAG; lag++) { + for (int col = 0; col < dimension; col++) { + if (!coeffByLag[row][lag][col].isZero()) { + hasDependency = true; + if (lag > maxLag) maxLag = lag; + } + } + } + if (!hasDependency) { + return new ArrayList(); + } + } + if (maxLag <= 0) { + return new ArrayList(); + } + + long[] bounds = resolveLoopBounds(node); + if (bounds == null) { + return new ArrayList(); + } + long min = bounds[0]; + long max = bounds[1]; + long recurrenceStart = min; + if (recurrenceStart < maxLag) { + recurrenceStart = maxLag; + } + if (recurrenceStart > max) { + return new ArrayList(); + } + + long seedStart = recurrenceStart - maxLag; + AutoStackingNumber[][] seedValues = new AutoStackingNumber[dimension][maxLag]; + for (int seq = 0; seq < dimension; seq++) { + NaturalArray arr = targetArrays.get(seq); + for (int offset = 0; offset < maxLag; offset++) { + long idxSeed = seedStart + offset; + Object seedObj = arr.get(idxSeed); + AutoStackingNumber seedNum = typeSystem.toAutoStackingNumber(seedObj); + if (seedNum == null) { + return new ArrayList(); + } + seedValues[seq][offset] = seedNum; + } + } + + AutoStackingNumber[][] flatCoefficients = new AutoStackingNumber[dimension][dimension * maxLag]; + for (int row = 0; row < dimension; row++) { + for (int lag = 1; lag <= maxLag; lag++) { + for (int col = 0; col < dimension; col++) { + int flatCol = ((lag - 1) * dimension) + col; + flatCoefficients[row][flatCol] = coeffByLag[row][lag][col]; + } + } + } + + PatternHandler.VectorRecurrencePattern pattern = new PatternHandler.VectorRecurrencePattern( + targetExprs, + dimension, + maxLag, + flatCoefficients, + constants, + recurrenceStart, + seedStart, + seedValues, + targetIndexByName + ); + + for (Expr targetExpr : targetExprs) { + results.add(new PatternHandler.PatternResult( + PatternHandler.PatternType.VECTOR_LINEAR_RECURRENCE, + pattern, + targetExpr + )); + } + return results; + } + public PatternHandler.LinearRecurrencePattern extractLinearRecurrencePattern(For node) { if (node == null || node.body == null || node.body.statements == null) { return null; @@ -444,6 +604,15 @@ private static class TermRef { TermRef(int lag) { this.lag = lag; } } + private static class VectorTermRef { + final int lag; + final int sequenceIndex; + VectorTermRef(int lag, int sequenceIndex) { + this.lag = lag; + this.sequenceIndex = sequenceIndex; + } + } + private TermRef extractIndexedTargetTerm(Expr expr, String targetArrayName, String iterator) { if (!(expr instanceof IndexAccess)) { return null; @@ -463,6 +632,111 @@ private TermRef extractIndexedTargetTerm(Expr expr, String targetArrayName, Stri return new TermRef(lag); } + private List collectVectorAssignments(For node) { + List assignments = new ArrayList(); + if (node == null || node.body == null || node.body.statements == null) { + return assignments; + } + for (Stmt stmt : node.body.statements) { + if (!(stmt instanceof Assignment)) { + return new ArrayList(); + } + Assignment assign = (Assignment) stmt; + if (assign.isDeclaration || !(assign.left instanceof IndexAccess)) { + return new ArrayList(); + } + IndexAccess access = (IndexAccess) assign.left; + if (!(access.array instanceof Identifier) || !(access.index instanceof Identifier)) { + return new ArrayList(); + } + Identifier idx = (Identifier) access.index; + if (!node.iterator.equals(idx.name)) { + return new ArrayList(); + } + assignments.add(assign); + } + return assignments; + } + + private boolean collectVectorLinearTerms( + Expr expr, + Map targetIndexByName, + String iterator, + AutoStackingNumber[][] coefficientsByLagAndSequence, + AutoStackingNumber[] constant, + AutoStackingNumber sign + ) { + if (expr == null) return false; + + if (expr instanceof BinaryOp) { + BinaryOp bin = (BinaryOp) expr; + if ("+".equals(bin.op)) { + return collectVectorLinearTerms(bin.left, targetIndexByName, iterator, coefficientsByLagAndSequence, constant, sign) && + collectVectorLinearTerms(bin.right, targetIndexByName, iterator, coefficientsByLagAndSequence, constant, sign); + } + if ("-".equals(bin.op)) { + return collectVectorLinearTerms(bin.left, targetIndexByName, iterator, coefficientsByLagAndSequence, constant, sign) && + collectVectorLinearTerms(bin.right, targetIndexByName, iterator, coefficientsByLagAndSequence, constant, + sign.multiply(AutoStackingNumber.fromLong(-1L))); + } + if ("*".equals(bin.op)) { + VectorTermRef ref = extractIndexedVectorTerm(bin.left, targetIndexByName, iterator); + AutoStackingNumber scalar = toNumericLiteral(bin.right); + if (ref == null || scalar == null) { + ref = extractIndexedVectorTerm(bin.right, targetIndexByName, iterator); + scalar = toNumericLiteral(bin.left); + } + if (ref != null && scalar != null) { + AutoStackingNumber delta = sign.multiply(scalar); + coefficientsByLagAndSequence[ref.lag][ref.sequenceIndex] = + coefficientsByLagAndSequence[ref.lag][ref.sequenceIndex].add(delta); + return true; + } + return false; + } + return false; + } + + VectorTermRef ref = extractIndexedVectorTerm(expr, targetIndexByName, iterator); + if (ref != null) { + coefficientsByLagAndSequence[ref.lag][ref.sequenceIndex] = + coefficientsByLagAndSequence[ref.lag][ref.sequenceIndex].add(sign); + return true; + } + + AutoStackingNumber literal = toNumericLiteral(expr); + if (literal != null) { + constant[0] = constant[0].add(sign.multiply(literal)); + return true; + } + + return false; + } + + private VectorTermRef extractIndexedVectorTerm( + Expr expr, + Map targetIndexByName, + String iterator + ) { + if (!(expr instanceof IndexAccess)) { + return null; + } + IndexAccess access = (IndexAccess) expr; + if (!(access.array instanceof Identifier)) { + return null; + } + String arrayName = ((Identifier) access.array).name; + Integer sequenceIndex = targetIndexByName.get(arrayName); + if (sequenceIndex == null) { + return null; + } + int lag = extractLag(access.index, iterator); + if (lag <= 0 || lag > MAX_SUPPORTED_LAG) { + return null; + } + return new VectorTermRef(lag, sequenceIndex.intValue()); + } + private int extractLag(Expr indexExpr, String iterator) { if (indexExpr instanceof BinaryOp) { BinaryOp bin = (BinaryOp) indexExpr; diff --git a/src/main/java/cod/interpreter/handler/PatternHandler.java b/src/main/java/cod/interpreter/handler/PatternHandler.java index 1d2c6a2..331dac4 100644 --- a/src/main/java/cod/interpreter/handler/PatternHandler.java +++ b/src/main/java/cod/interpreter/handler/PatternHandler.java @@ -10,6 +10,7 @@ import cod.range.formula.ConditionalFormula; import cod.range.formula.LinearRecurrenceFormula; import cod.range.formula.SequenceFormula; +import cod.range.formula.VectorRecurrenceFormula; import cod.range.pattern.ConditionalPattern; import cod.range.pattern.SequencePattern; @@ -19,7 +20,8 @@ public class PatternHandler { public enum PatternType { CONDITIONAL, SEQUENCE, - LINEAR_RECURRENCE + LINEAR_RECURRENCE, + VECTOR_LINEAR_RECURRENCE } public static class PatternResult { @@ -65,6 +67,40 @@ public LinearRecurrencePattern( } } + public static class VectorRecurrencePattern { + public final List targetArrays; + public final int dimension; + public final int order; + public final AutoStackingNumber[][] coefficients; + public final AutoStackingNumber[] constantTerms; + public final long recurrenceStart; + public final long seedStart; + public final AutoStackingNumber[][] seedValues; + public final Map targetIndexByName; + + public VectorRecurrencePattern( + List targetArrays, + int dimension, + int order, + AutoStackingNumber[][] coefficients, + AutoStackingNumber[] constantTerms, + long recurrenceStart, + long seedStart, + AutoStackingNumber[][] seedValues, + Map targetIndexByName + ) { + this.targetArrays = targetArrays; + this.dimension = dimension; + this.order = order; + this.coefficients = coefficients; + this.constantTerms = constantTerms; + this.recurrenceStart = recurrenceStart; + this.seedStart = seedStart; + this.seedValues = seedValues; + this.targetIndexByName = targetIndexByName; + } + } + private final InterpreterVisitor dispatcher; private final TypeHandler typeSystem; private final ExpressionHandler expressionHandler; @@ -95,6 +131,10 @@ public Object applyPatterns(For node, List patterns) { } try { + if (isVectorRecurrencePatternSet(patterns)) { + return applyVectorRecurrencePatterns(node, patterns); + } + List targetArrays = new ArrayList(); List> groupedPatterns = new ArrayList>(); Map arrayIdToGroupIndex = new HashMap(); @@ -285,4 +325,103 @@ public void applyLinearRecurrencePattern( throw new InternalError("Failed to apply linear recurrence pattern", e); } } + + private boolean isVectorRecurrencePatternSet(List patterns) { + if (patterns == null || patterns.isEmpty()) return false; + for (PatternResult result : patterns) { + if (result == null || result.type != PatternType.VECTOR_LINEAR_RECURRENCE) { + return false; + } + } + return true; + } + + private Object applyVectorRecurrencePatterns(For node, List patterns) { + PatternResult first = patterns.get(0); + if (!(first.pattern instanceof VectorRecurrencePattern)) { + throw new InternalError("Invalid vector recurrence pattern payload"); + } + VectorRecurrencePattern pattern = (VectorRecurrencePattern) first.pattern; + + long start = 0L; + long end = 0L; + boolean boundsFound = false; + + if (node.range != null) { + Object startObj = dispatcher.dispatch(node.range.start); + Object endObj = dispatcher.dispatch(node.range.end); + start = expressionHandler.toLong(startObj); + end = expressionHandler.toLong(endObj); + boundsFound = true; + } else if (node.arraySource != null) { + Object sourceObj = dispatcher.dispatch(node.arraySource); + sourceObj = typeSystem.unwrap(sourceObj); + if (sourceObj instanceof NaturalArray) { + NaturalArray sourceArr = (NaturalArray) sourceObj; + if (sourceArr.size() > 0) { + start = 0L; + end = sourceArr.size() - 1L; + boundsFound = true; + } + } else if (sourceObj instanceof List) { + List sourceList = (List) sourceObj; + if (!sourceList.isEmpty()) { + start = 0L; + end = sourceList.size() - 1L; + boundsFound = true; + } + } + } + + if (!boundsFound) { + DebugSystem.debug("OPTIMIZER", "Vector recurrence: unable to resolve loop bounds"); + return arrayOperationHandler.executeForLoopNormally(node); + } + + long min = Math.min(start, end); + long max = Math.max(start, end); + long formulaStart = Math.max(min, pattern.seedStart); + long formulaEnd = max; + if (formulaEnd < formulaStart) { + return arrayOperationHandler.executeForLoopNormally(node); + } + + VectorRecurrenceFormula formula = new VectorRecurrenceFormula( + formulaStart, + formulaEnd, + pattern.recurrenceStart, + pattern.seedStart, + pattern.dimension, + pattern.order, + pattern.coefficients, + pattern.constantTerms, + pattern.seedValues + ); + + List attachedArrays = new ArrayList(); + for (Expr targetExpr : pattern.targetArrays) { + Object resolvedArray = dispatcher.dispatch(targetExpr); + resolvedArray = typeSystem.unwrap(resolvedArray); + if (!(resolvedArray instanceof NaturalArray)) { + DebugSystem.debug("OPTIMIZER", "Vector recurrence target not NaturalArray; fallback"); + return arrayOperationHandler.executeForLoopNormally(node); + } + NaturalArray arr = (NaturalArray) resolvedArray; + if (!(targetExpr instanceof Identifier)) { + return arrayOperationHandler.executeForLoopNormally(node); + } + String name = ((Identifier) targetExpr).name; + Integer seqIndex = pattern.targetIndexByName.get(name); + if (seqIndex == null) { + return arrayOperationHandler.executeForLoopNormally(node); + } + arr.addVectorRecurrenceFormula(formula, seqIndex.intValue()); + attachedArrays.add(arr); + } + + if (attachedArrays.isEmpty()) { + return arrayOperationHandler.executeForLoopNormally(node); + } + return attachedArrays.get(attachedArrays.size() - 1); + } } diff --git a/src/main/java/cod/range/NaturalArray.java b/src/main/java/cod/range/NaturalArray.java index 9151905..bc572ab 100644 --- a/src/main/java/cod/range/NaturalArray.java +++ b/src/main/java/cod/range/NaturalArray.java @@ -63,6 +63,7 @@ public class NaturalArray { private List sequenceFormulas = new ArrayList(); private List conditionalFormulas = new ArrayList(); private List linearRecurrenceFormulas = new ArrayList(); + private List vectorRecurrenceFormulas = new ArrayList(); private Map computedCache = new HashMap(); // Pending updates for lazy assignment @@ -236,6 +237,16 @@ public int compareTo(PendingRangeUpdate other) { } } + private static class VectorRecurrenceBinding { + final VectorRecurrenceFormula formula; + final int sequenceIndex; + + VectorRecurrenceBinding(VectorRecurrenceFormula formula, int sequenceIndex) { + this.formula = formula; + this.sequenceIndex = sequenceIndex; + } + } + // ========== CONSTRUCTORS ========== public NaturalArray(Range range, Evaluator evaluator, ExecutionContext context) { @@ -832,6 +843,15 @@ public Object get(long index) { } // Then linear recurrence formulas + Object vectorRecurrenceResult = evaluateVectorRecurrenceFormulas(index); + if (vectorRecurrenceResult != null) { + lastIndex = index; + lastValue = vectorRecurrenceResult; + updateRecentCache(index, vectorRecurrenceResult); + return maybeConvert(vectorRecurrenceResult); + } + + // Then scalar linear recurrence formulas Object recurrenceResult = evaluateLinearRecurrenceFormulas(index); if (recurrenceResult != null) { lastIndex = index; @@ -1437,6 +1457,22 @@ public void addLinearRecurrenceFormula(LinearRecurrenceFormula formula) { clearCache(); } + public void addVectorRecurrenceFormula(VectorRecurrenceFormula formula, int sequenceIndex) { + if (formula == null) { + throw new InternalError("Attempted to add null VectorRecurrenceFormula"); + } + if (sequenceIndex < 0 || sequenceIndex >= formula.dimension) { + throw new ProgramError("Invalid vector recurrence sequence index: " + sequenceIndex); + } + + if (tracked) { + ArrayTracker.recordFormulaApplication(this); + } + + vectorRecurrenceFormulas.add(new VectorRecurrenceBinding(formula, sequenceIndex)); + clearCache(); + } + public void clearCache() { if (computedCache != null) { computedCache.clear(); @@ -1537,6 +1573,35 @@ private Object evaluateLinearRecurrenceFormulas(long index) { return null; } + private Object evaluateVectorRecurrenceFormulas(long index) { + if (vectorRecurrenceFormulas.isEmpty()) return null; + + for (int i = vectorRecurrenceFormulas.size() - 1; i >= 0; i--) { + VectorRecurrenceBinding binding = vectorRecurrenceFormulas.get(i); + if (binding == null || binding.formula == null) { + throw new InternalError("Null VectorRecurrenceFormula binding in list"); + } + if (binding.formula.contains(index)) { + try { + Object result = binding.formula.evaluate(index, binding.sequenceIndex); + if (result != null) { + if (computedCache == null) { + computedCache = new HashMap(); + } + computedCache.put(index, result); + } + return result; + } catch (ProgramError e) { + throw e; + } catch (Exception e) { + throw new InternalError( + "Vector recurrence formula evaluation failed at index " + index, e); + } + } + } + return null; + } + // ========== OUTPUT CACHING METHODS ========== public void recordOutput(long index, Object value) { @@ -1694,6 +1759,9 @@ public String toString() { if (!linearRecurrenceFormulas.isEmpty()) { sb.append("\n Linear recurrence formulas: ").append(linearRecurrenceFormulas.size()); } + if (!vectorRecurrenceFormulas.isEmpty()) { + sb.append("\n Vector recurrence formulas: ").append(vectorRecurrenceFormulas.size()); + } return sb.toString(); } catch (ProgramError e) { diff --git a/src/main/java/cod/range/formula/VectorRecurrenceFormula.java b/src/main/java/cod/range/formula/VectorRecurrenceFormula.java new file mode 100644 index 0000000..040b930 --- /dev/null +++ b/src/main/java/cod/range/formula/VectorRecurrenceFormula.java @@ -0,0 +1,260 @@ +package cod.range.formula; + +import cod.math.AutoStackingNumber; + +import java.util.Arrays; + +public class VectorRecurrenceFormula { + public final long start; + public final long end; + public final long recurrenceStart; + public final long seedStartIndex; + public final int dimension; + public final int order; + public final AutoStackingNumber[][] coefficients; + public final AutoStackingNumber[] constant; + public final AutoStackingNumber[][] seedValues; + private final boolean hasConstantTerm; + private transient long rollingIndex = Long.MIN_VALUE; + private transient AutoStackingNumber[] rollingState = null; + + private static final AutoStackingNumber ZERO = AutoStackingNumber.fromLong(0L); + private static final AutoStackingNumber ONE = AutoStackingNumber.fromLong(1L); + + public VectorRecurrenceFormula( + long start, + long end, + long recurrenceStart, + long seedStartIndex, + int dimension, + int order, + AutoStackingNumber[][] coefficients, + AutoStackingNumber[] constant, + AutoStackingNumber[][] seedValues + ) { + this.start = start; + this.end = end; + this.recurrenceStart = recurrenceStart; + this.seedStartIndex = seedStartIndex; + this.dimension = dimension; + this.order = order; + this.coefficients = coefficients; + this.constant = constant != null ? constant : zerosVector(dimension); + this.seedValues = seedValues; + this.hasConstantTerm = hasNonZeroConstant(this.constant); + resetRollingState(); + } + + public boolean contains(long index) { + return index >= start && index <= end; + } + + public Object evaluate(long index, int sequenceIndex) { + if (sequenceIndex < 0 || sequenceIndex >= dimension) { + return null; + } + if (order <= 0 || dimension <= 0 || coefficients == null || seedValues == null) { + return null; + } + if (seedValues.length != dimension) { + return null; + } + for (int i = 0; i < dimension; i++) { + if (seedValues[i] == null || seedValues[i].length != order) { + return null; + } + } + + if (index < recurrenceStart) { + int offset = (int) (index - seedStartIndex); + if (offset < 0 || offset >= order) { + return null; + } + return seedValues[sequenceIndex][offset]; + } + + synchronized (this) { + if (rollingState != null && index == rollingIndex) { + return rollingState[sequenceIndex]; + } + if (rollingState != null && index == rollingIndex + 1L) { + advanceRollingState(); + rollingIndex = index; + return rollingState[sequenceIndex]; + } + } + + long lastSeedIndex = recurrenceStart - 1L; + long steps = index - lastSeedIndex; + int baseDim = dimension * order; + int matrixDim = hasConstantTerm ? baseDim + 1 : baseDim; + + AutoStackingNumber[][] transition = buildTransition(baseDim, matrixDim); + AutoStackingNumber[] state = buildBaseState(baseDim, matrixDim); + AutoStackingNumber[][] power = matrixPow(transition, steps); + AutoStackingNumber[] result = multiply(power, state); + + synchronized (this) { + rollingState = Arrays.copyOf(result, baseDim); + rollingIndex = index; + return rollingState[sequenceIndex]; + } + } + + private AutoStackingNumber[][] buildTransition(int baseDim, int matrixDim) { + AutoStackingNumber[][] transition = new AutoStackingNumber[matrixDim][matrixDim]; + for (int i = 0; i < matrixDim; i++) { + for (int j = 0; j < matrixDim; j++) { + transition[i][j] = ZERO; + } + } + + for (int row = 0; row < dimension; row++) { + AutoStackingNumber[] coeffRow = coefficients[row]; + if (coeffRow == null || coeffRow.length != baseDim) { + continue; + } + for (int col = 0; col < baseDim; col++) { + AutoStackingNumber c = coeffRow[col]; + transition[row][col] = c != null ? c : ZERO; + } + } + + for (int block = 1; block < order; block++) { + for (int seq = 0; seq < dimension; seq++) { + int row = (block * dimension) + seq; + int col = ((block - 1) * dimension) + seq; + transition[row][col] = ONE; + } + } + + if (hasConstantTerm) { + int constCol = matrixDim - 1; + for (int row = 0; row < dimension; row++) { + AutoStackingNumber c = constant[row]; + transition[row][constCol] = c != null ? c : ZERO; + } + transition[constCol][constCol] = ONE; + } + return transition; + } + + private AutoStackingNumber[] buildBaseState(int baseDim, int matrixDim) { + AutoStackingNumber[] state = new AutoStackingNumber[matrixDim]; + for (int i = 0; i < matrixDim; i++) { + state[i] = ZERO; + } + for (int block = 0; block < order; block++) { + long sourceIndex = (recurrenceStart - 1L) - block; + int seedOffset = (int) (sourceIndex - seedStartIndex); + for (int seq = 0; seq < dimension; seq++) { + state[(block * dimension) + seq] = seedValues[seq][seedOffset]; + } + } + if (hasConstantTerm) { + state[matrixDim - 1] = ONE; + } + return state; + } + + private void advanceRollingState() { + int baseDim = dimension * order; + AutoStackingNumber[] nextState = new AutoStackingNumber[baseDim]; + + for (int row = 0; row < dimension; row++) { + AutoStackingNumber sum = constant[row] != null ? constant[row] : ZERO; + AutoStackingNumber[] coeffRow = coefficients[row]; + for (int col = 0; col < baseDim; col++) { + AutoStackingNumber c = coeffRow[col]; + if (c != null && !c.isZero()) { + sum = sum.add(c.multiply(rollingState[col])); + } + } + nextState[row] = sum; + } + + for (int block = 1; block < order; block++) { + for (int seq = 0; seq < dimension; seq++) { + nextState[(block * dimension) + seq] = rollingState[((block - 1) * dimension) + seq]; + } + } + + rollingState = nextState; + } + + private AutoStackingNumber[][] matrixPow(AutoStackingNumber[][] base, long exp) { + int dim = base.length; + AutoStackingNumber[][] result = identity(dim); + AutoStackingNumber[][] current = base; + long e = exp; + while (e > 0) { + if ((e & 1L) == 1L) { + result = multiply(result, current); + } + e >>= 1; + if (e > 0) { + current = multiply(current, current); + } + } + return result; + } + + private AutoStackingNumber[][] identity(int dim) { + AutoStackingNumber[][] id = new AutoStackingNumber[dim][dim]; + for (int i = 0; i < dim; i++) { + for (int j = 0; j < dim; j++) { + id[i][j] = (i == j) ? ONE : ZERO; + } + } + return id; + } + + private AutoStackingNumber[][] multiply(AutoStackingNumber[][] a, AutoStackingNumber[][] b) { + int n = a.length; + AutoStackingNumber[][] out = new AutoStackingNumber[n][n]; + for (int i = 0; i < n; i++) { + for (int j = 0; j < n; j++) { + AutoStackingNumber sum = ZERO; + for (int k = 0; k < n; k++) { + sum = sum.add(a[i][k].multiply(b[k][j])); + } + out[i][j] = sum; + } + } + return out; + } + + private AutoStackingNumber[] multiply(AutoStackingNumber[][] a, AutoStackingNumber[] v) { + int n = a.length; + AutoStackingNumber[] out = new AutoStackingNumber[n]; + for (int i = 0; i < n; i++) { + AutoStackingNumber sum = ZERO; + for (int k = 0; k < n; k++) { + sum = sum.add(a[i][k].multiply(v[k])); + } + out[i] = sum; + } + return out; + } + + private static boolean hasNonZeroConstant(AutoStackingNumber[] constantVector) { + if (constantVector == null) return false; + for (AutoStackingNumber n : constantVector) { + if (n != null && !n.isZero()) return true; + } + return false; + } + + private static AutoStackingNumber[] zerosVector(int length) { + AutoStackingNumber[] out = new AutoStackingNumber[length]; + for (int i = 0; i < length; i++) { + out[i] = ZERO; + } + return out; + } + + private void resetRollingState() { + rollingIndex = Long.MIN_VALUE; + rollingState = null; + } +} From 38106e05eb8349d8eaa9b0443d2c500147ee9ca1 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 14:16:59 +0000 Subject: [PATCH 10/13] Add vector recurrence optimization parity test Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/6399c570-b95d-4d37-a5ef-4f2b988df11d Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- .../VectorLinearRecurrenceOptimization.cod | 43 +++++++++++++++++++ 1 file changed, 43 insertions(+) create mode 100644 src/main/cod/demo/src/main/test/linearrecurrenceoptimization/VectorLinearRecurrenceOptimization.cod diff --git a/src/main/cod/demo/src/main/test/linearrecurrenceoptimization/VectorLinearRecurrenceOptimization.cod b/src/main/cod/demo/src/main/test/linearrecurrenceoptimization/VectorLinearRecurrenceOptimization.cod new file mode 100644 index 0000000..a9d5cec --- /dev/null +++ b/src/main/cod/demo/src/main/test/linearrecurrenceoptimization/VectorLinearRecurrenceOptimization.cod @@ -0,0 +1,43 @@ +unit test.linearrecurrenceoptimization + +share main() { + out("=== Vector linear recurrence optimization ===") + start := timer() + + a := [0 to 200] + b := [0 to 200] + + a[0] = 1 + a[1] = 2 + b[0] = 0 + b[1] = 1 + + for i of [2 to 200] { + a[i] = a[i-1] + b[i-1] + b[i] = a[i-1] - b[i-1] + } + + out("pair1-a[10]=" + a[10] + " expected=48") + out("pair1-b[10]=" + b[10] + " expected=16") + out("pair1-a[20]=" + a[20] + " expected=1536") + out("pair1-b[20]=" + b[20] + " expected=512") + + c := [0 to 200] + d := [0 to 200] + + c[0] = 1 + c[1] = 2 + d[0] = 3 + d[1] = 4 + + for i of [2 to 200] { + c[i] = c[i-1] + d[i-2] + d[i] = 2 * c[i-2] - d[i-1] + 3 + } + + out("pair2-c[10]=" + c[10] + " expected=95") + out("pair2-d[10]=" + d[10] + " expected=41") + out("pair2-c[20]=" + c[20] + " expected=3070") + out("pair2-d[20]=" + d[20] + " expected=1367") + out("elapsed_ms=" + (timer() - start)) +} From 75c9510fc272b17ff9e88a57f151574ac4175996 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 14:19:01 +0000 Subject: [PATCH 11/13] Fix vector recurrence seed offset safety Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/6399c570-b95d-4d37-a5ef-4f2b988df11d Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- .../handler/LoopOptimizationHandler.java | 8 +++---- .../formula/VectorRecurrenceFormula.java | 21 ++++++++++++++++--- 2 files changed, 22 insertions(+), 7 deletions(-) diff --git a/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java b/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java index 447d111..e38c85f 100644 --- a/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java +++ b/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java @@ -400,8 +400,8 @@ public List extractVectorLinearRecurrencePatterns( for (int seq = 0; seq < dimension; seq++) { NaturalArray arr = targetArrays.get(seq); for (int offset = 0; offset < maxLag; offset++) { - long idxSeed = seedStart + offset; - Object seedObj = arr.get(idxSeed); + long seedIndex = seedStart + offset; + Object seedObj = arr.get(seedIndex); AutoStackingNumber seedNum = typeSystem.toAutoStackingNumber(seedObj); if (seedNum == null) { return new ArrayList(); @@ -527,8 +527,8 @@ public PatternHandler.LinearRecurrencePattern extractLinearRecurrencePattern(For AutoStackingNumber[] seed = new AutoStackingNumber[order]; long seedStart = recurrenceStart - order; for (int i = 0; i < order; i++) { - long idxSeed = seedStart + i; - Object vObj = targetArray.get(idxSeed); + long seedIndex = seedStart + i; + Object vObj = targetArray.get(seedIndex); AutoStackingNumber v = typeSystem.toAutoStackingNumber(vObj); if (v == null) { return null; diff --git a/src/main/java/cod/range/formula/VectorRecurrenceFormula.java b/src/main/java/cod/range/formula/VectorRecurrenceFormula.java index 040b930..46be8b5 100644 --- a/src/main/java/cod/range/formula/VectorRecurrenceFormula.java +++ b/src/main/java/cod/range/formula/VectorRecurrenceFormula.java @@ -66,8 +66,12 @@ public Object evaluate(long index, int sequenceIndex) { } if (index < recurrenceStart) { - int offset = (int) (index - seedStartIndex); - if (offset < 0 || offset >= order) { + Long offsetLong = safeToIntOffset(index - seedStartIndex); + if (offsetLong == null) { + return null; + } + int offset = offsetLong.intValue(); + if (offset >= order) { return null; } return seedValues[sequenceIndex][offset]; @@ -146,7 +150,11 @@ private AutoStackingNumber[] buildBaseState(int baseDim, int matrixDim) { } for (int block = 0; block < order; block++) { long sourceIndex = (recurrenceStart - 1L) - block; - int seedOffset = (int) (sourceIndex - seedStartIndex); + Long seedOffsetLong = safeToIntOffset(sourceIndex - seedStartIndex); + if (seedOffsetLong == null) { + return null; + } + int seedOffset = seedOffsetLong.intValue(); for (int seq = 0; seq < dimension; seq++) { state[(block * dimension) + seq] = seedValues[seq][seedOffset]; } @@ -253,6 +261,13 @@ private static AutoStackingNumber[] zerosVector(int length) { return out; } + private Long safeToIntOffset(long value) { + if (value < 0L || value > Integer.MAX_VALUE) { + return null; + } + return Long.valueOf(value); + } + private void resetRollingState() { rollingIndex = Long.MIN_VALUE; rollingState = null; From 71b4afcf385862631a5a37647977491ac4c99b4b Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 14:21:38 +0000 Subject: [PATCH 12/13] Plan final cleanup after validation timeout Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/6399c570-b95d-4d37-a5ef-4f2b988df11d Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- source_.jar | Bin 383203 -> 388233 bytes .../__StaticModule__.codb | Bin 35008 -> 36500 bytes .../handler/LoopOptimizationHandler.java | 4 ++-- .../formula/VectorRecurrenceFormula.java | 20 ++++++++---------- 4 files changed, 11 insertions(+), 13 deletions(-) diff --git a/source_.jar b/source_.jar index d8e3af8b7db6ed7ce04aec0ca834716b805cf610..eee8023cfa9a85e0a8bdb40ca8809aa604ec26d1 100644 GIT binary patch delta 28319 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⁣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 diff --git a/src/main/cod/demo/src/bin/test.linearrecurrenceoptimization/__StaticModule__.codb b/src/main/cod/demo/src/bin/test.linearrecurrenceoptimization/__StaticModule__.codb index 9629f4d85c451dfe9b16bff8ebfeb441b98093f5..1b6db51089e7db7cf087783f4de638467ab0a9e8 100644 GIT binary patch delta 3326 zcmbuAX;4#F6vufi$`*vW5Mr=E1Vo3$DzX@mf;H2!i-H0I5!tJ3!w!)sq6ngLDr2!M z)uKfiK%=!-Kpa7FtI(+%ElOz>a9}{R1w~5leJ|0MnDC_^GLw1tod5aVbN~0A*2BtQ zl`A(~QYH+5&n^OrM`yQ1{F2_pEx`5=ayb`(GTX znWtM&=W$`MTAx)q5>PvKJkYC41Xt#>!N`4B)TGK(X4HrO?vYOn6(Jd7Saj6LgqRcN z+`%+IaL5pSQn9XTh8}GuwAixX#H{5g{0RzwQH{f|&lKJ!tz4o}4Nn%EL#W+p*#%Fu zpangeo^a4r3x3vPi-Tx|&S|6)(xpo@$TU%p=BPa22tpZhIcKCxiKZBOScbM?sBr!V zDr2?bW8F&W0_4hjVj9fMGP;mpVF;H$O_DDsvUXWcFuOYD8*vJ+GEo<`qmTFb>e<)q zw|IGf5jvVCX}}TIZn8#>dPwMvy59DY`7kurO3#=j(|~@1g1ba z+&R}yX#_`A@@`S zZ3I=faMVv%^j*!))$(2+;xOdXIw$DB16DLE<4s1?)5y!7C`)I1_o5@ptYWssu7J)B z-qPxyynVz=Ud!QPbq`ldBK1{8jLuvGFZs}7bpu_m*X)?A1}l`s(7C5#kWuEC^2GtK zO;%VOyBnHRv0EP_w~maVDB|!;Zk3q(5en~5#^L%ig=2Hml%>rrwV=q{v_d%BGg}K9 zG_E08sfBmhS~Upl$e$SO0SaV`W|?Ns?0Xu8#IUqaGQOu36;(JB1nm~mmSBoeiF~$- z{MjviCfx*-_z^)fKRxmNEwh9X&DG-VvZ>3^x6pQSc5s>#+MKrM0^5`u%=AWW9^oi9 z0F7GW+QR;cSg(qGIN|%rRjl&7Y3|U8v`}eZiMoI6{?%XO2OM=Rdd4c3nu$Q(OX$0He1%&rf%1{87a(q2OA z{AO8ixPwHzE_g?@igoL^SX@{gkj!8#xz#?k$R=d7SUhMpu@ZdanNTkBa0}l3OY9<5c zhf+Z=-3scWIA}|>HwnZd=6;51DeKO^79x>_eWjhz^HO7SMoK$5L2KiUdvjkUc-mw| z_1)?sReDo0kqZ4qClZ`s)Zc>~D$}V}AU~qlNe9lvI+G&@(@;@#8cJtch7o_Ia=(Gz zP3V8LnVkCLaltUY*$HeS%@x1(XT!Nr9moZnFcVM@;_IkipPGFkHn0J0Te&R;jPsqC zn-x9#=ommR*r_Bc5!!>fU=(T&oGpAgte9j~2t}fBJYbT)LMRemC?e?~5D7mUlc@Vs zB#I^lCh-X)NmTim#1z8#+dk+?8DwmwC=^bUKXRO42_kXfn?Pas);azwg$8cTZ$Cp6 zD$DN_VT_rEicsJKrP~llGI&I+CP7X`U=Zm;ErY9(6o|sXgF%v_D3H(NFh~vp`8xxH zFxvK!{ZKT2fC#fj*USVqd`Y5cZeJ~SI_({kI34b7+$dh9JxA|W?V|4@e0rXIZ_7r= z_cpzPM8`ARLF|0lRk4QD+`;z*pKru=+*aAD<8dLda|bdJ^1Q+)9kjYEB`lppS&%`YBxQWqm1D3!lj?}Vv4Jt{vnY(REQ~RU zF#4J>Mn~rX()BY;4-9fDn*`aCLxD8reAtsR=n_!1NVAC~5s hf>Ay&GEj}X)3`?A+g*S~hVw`fpFKL{13$U9{Xf9z3iJQ~ delta 3531 zcmbVOdo+}39PXQ8mANp;%rM!oXdDfZ3ggldvTi9Ml?s`nOpPs<2%9d5I6v#0t%y2Z z&gw!_TU$$1E8V10PB&e)I(1r3_tdHE`+lEsGBe-&(O+}U`#!(teSVkk_e^Cqqosn; zaDqVyfM>fIf|#DJLCzirB#+l*jTkY)ep=uy?!y^VZ3Lsv&TEg0b7xr!PoPle_C-bDL=-l1rt_Ny-iK{_P{iNrXtD$n z{|tVjtUtv`@fP9PUHmAEYCXQRJVLktmm7>7dzFVmClF?zyIu*Zq|xUvYn^ZWWyjW{ zRvOk;i&Q-?Yr|#_#SU}V$!qKb3?5o`s-*& zL%0S5YYmRH=tmVjc>5!tA%5mJw=M*i47=#Qy%%6ku~Q+K-Z|h z0>=;UPyQ`t2+_R!J?7ocz89C}R@g+t+bZgxe`Mv(=QH~d*tlbI#Wk~Tadol$cGdI( z`Q@QT@Wk0M!Dfc-8xczXZEd2$o4ysASoLPmAikp=TA1ogcEF0TN#JLy(7aWuK4C3a zEgonWJdyICRx}36*@O{ zi>t{YR5b%FE_)bfsSDum+9}Fo`*A9Vs!wkK_bS z32I|o3tV+Pvcr`#_+feRSM>C!Og^_Bg|c_=jIgL~(vv>?^aJ@#4Xp)pvD=01d;Itg z2xSUcrozglPzcU_be6`hHKII(U{W?2oA1X1e3`C^rLI21~*KxJ)Y zx<26sJedGGR#-z=%%Sh`jjK5l9Ih;kE!Nn@K&%qLfWj9N6tf{MBU@ujHYS^c%P;Aq zQA8}*M{_SGO~N47l;*TJkvp=TX>c?p=@IGyqbd?GSEp~m}9HH+woK?2NYaF<3fEL)i*qK|Lr)&L$^GM zhDS9#5%6*amAY0d!Kv4*q*A|^iBn&LQh#lVQSWKNk39Q2O>1Qu?$z6xJ8D9_zD#C_nOO5gksbayme diff --git a/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java b/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java index e38c85f..e67620f 100644 --- a/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java +++ b/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java @@ -528,8 +528,8 @@ public PatternHandler.LinearRecurrencePattern extractLinearRecurrencePattern(For long seedStart = recurrenceStart - order; for (int i = 0; i < order; i++) { long seedIndex = seedStart + i; - Object vObj = targetArray.get(seedIndex); - AutoStackingNumber v = typeSystem.toAutoStackingNumber(vObj); + Object seedValue = targetArray.get(seedIndex); + AutoStackingNumber v = typeSystem.toAutoStackingNumber(seedValue); if (v == null) { return null; } diff --git a/src/main/java/cod/range/formula/VectorRecurrenceFormula.java b/src/main/java/cod/range/formula/VectorRecurrenceFormula.java index 46be8b5..52e4b33 100644 --- a/src/main/java/cod/range/formula/VectorRecurrenceFormula.java +++ b/src/main/java/cod/range/formula/VectorRecurrenceFormula.java @@ -66,15 +66,14 @@ public Object evaluate(long index, int sequenceIndex) { } if (index < recurrenceStart) { - Long offsetLong = safeToIntOffset(index - seedStartIndex); - if (offsetLong == null) { + Integer seedOffset = validateOffsetInIntRange(index - seedStartIndex); + if (seedOffset == null) { return null; } - int offset = offsetLong.intValue(); - if (offset >= order) { + if (seedOffset.intValue() >= order) { return null; } - return seedValues[sequenceIndex][offset]; + return seedValues[sequenceIndex][seedOffset.intValue()]; } synchronized (this) { @@ -150,13 +149,12 @@ private AutoStackingNumber[] buildBaseState(int baseDim, int matrixDim) { } for (int block = 0; block < order; block++) { long sourceIndex = (recurrenceStart - 1L) - block; - Long seedOffsetLong = safeToIntOffset(sourceIndex - seedStartIndex); - if (seedOffsetLong == null) { + Integer seedOffset = validateOffsetInIntRange(sourceIndex - seedStartIndex); + if (seedOffset == null) { return null; } - int seedOffset = seedOffsetLong.intValue(); for (int seq = 0; seq < dimension; seq++) { - state[(block * dimension) + seq] = seedValues[seq][seedOffset]; + state[(block * dimension) + seq] = seedValues[seq][seedOffset.intValue()]; } } if (hasConstantTerm) { @@ -261,11 +259,11 @@ private static AutoStackingNumber[] zerosVector(int length) { return out; } - private Long safeToIntOffset(long value) { + private Integer validateOffsetInIntRange(long value) { if (value < 0L || value > Integer.MAX_VALUE) { return null; } - return Long.valueOf(value); + return Integer.valueOf((int) value); } private void resetRollingState() { From fa058543b745cfe277c116650cfffa766160b765 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 12 Apr 2026 14:22:26 +0000 Subject: [PATCH 13/13] Finalize vector recurrence cleanup and artifact reset Agent-Logs-Url: https://github.com/DanexCodr/Coderive/sessions/6399c570-b95d-4d37-a5ef-4f2b988df11d Co-authored-by: DanexCodr <216312766+DanexCodr@users.noreply.github.com> --- source_.jar | Bin 388233 -> 383203 bytes .../__StaticModule__.codb | Bin 36500 -> 35008 bytes .../handler/LoopOptimizationHandler.java | 4 ++- .../formula/VectorRecurrenceFormula.java | 26 ++++++++---------- 4 files changed, 14 insertions(+), 16 deletions(-) diff --git a/source_.jar b/source_.jar index eee8023cfa9a85e0a8bdb40ca8809aa604ec26d1..d8e3af8b7db6ed7ce04aec0ca834716b805cf610 100644 GIT binary patch delta 23286 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 delta 28319 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⁣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 delta 3326 zcmbuAX;4#F6vufi$`*vW5Mr=E1Vo3$DzX@mf;H2!i-H0I5!tJ3!w!)sq6ngLDr2!M z)uKfiK%=!-Kpa7FtI(+%ElOz>a9}{R1w~5leJ|0MnDC_^GLw1tod5aVbN~0A*2BtQ zl`A(~QYH+5&n^OrM`yQ1{F2_pEx`5=ayb`(GTX znWtM&=W$`MTAx)q5>PvKJkYC41Xt#>!N`4B)TGK(X4HrO?vYOn6(Jd7Saj6LgqRcN z+`%+IaL5pSQn9XTh8}GuwAixX#H{5g{0RzwQH{f|&lKJ!tz4o}4Nn%EL#W+p*#%Fu zpangeo^a4r3x3vPi-Tx|&S|6)(xpo@$TU%p=BPa22tpZhIcKCxiKZBOScbM?sBr!V zDr2?bW8F&W0_4hjVj9fMGP;mpVF;H$O_DDsvUXWcFuOYD8*vJ+GEo<`qmTFb>e<)q zw|IGf5jvVCX}}TIZn8#>dPwMvy59DY`7kurO3#=j(|~@1g1ba z+&R}yX#_`A@@`S zZ3I=faMVv%^j*!))$(2+;xOdXIw$DB16DLE<4s1?)5y!7C`)I1_o5@ptYWssu7J)B z-qPxyynVz=Ud!QPbq`ldBK1{8jLuvGFZs}7bpu_m*X)?A1}l`s(7C5#kWuEC^2GtK zO;%VOyBnHRv0EP_w~maVDB|!;Zk3q(5en~5#^L%ig=2Hml%>rrwV=q{v_d%BGg}K9 zG_E08sfBmhS~Upl$e$SO0SaV`W|?Ns?0Xu8#IUqaGQOu36;(JB1nm~mmSBoeiF~$- z{MjviCfx*-_z^)fKRxmNEwh9X&DG-VvZ>3^x6pQSc5s>#+MKrM0^5`u%=AWW9^oi9 z0F7GW+QR;cSg(qGIN|%rRjl&7Y3|U8v`}eZiMoI6{?%XO2OM=Rdd4c3nu$Q(OX$0He1%&rf%1{87a(q2OA z{AO8ixPwHzE_g?@igoL^SX@{gkj!8#xz#?k$R=d7SUhMpu@ZdanNTkBa0}l3OY9<5c zhf+Z=-3scWIA}|>HwnZd=6;51DeKO^79x>_eWjhz^HO7SMoK$5L2KiUdvjkUc-mw| z_1)?sReDo0kqZ4qClZ`s)Zc>~D$}V}AU~qlNe9lvI+G&@(@;@#8cJtch7o_Ia=(Gz zP3V8LnVkCLaltUY*$HeS%@x1(XT!Nr9moZnFcVM@;_IkipPGFkHn0J0Te&R;jPsqC zn-x9#=ommR*r_Bc5!!>fU=(T&oGpAgte9j~2t}fBJYbT)LMRemC?e?~5D7mUlc@Vs zB#I^lCh-X)NmTim#1z8#+dk+?8DwmwC=^bUKXRO42_kXfn?Pas);azwg$8cTZ$Cp6 zD$DN_VT_rEicsJKrP~llGI&I+CP7X`U=Zm;ErY9(6o|sXgF%v_D3H(NFh~vp`8xxH zFxvK!{ZKT2fC#fj*USVqd`Y5cZeJ~SI_({kI34b7+$dh9JxA|W?V|4@e0rXIZ_7r= z_cpzPM8`ARLF|0lRk4QD+`;z*pKru=+*aAD<8dLda|bdJ^1Q+)9kjYEB`lppS&%`YBxQWqm1D3!lj?}Vv4Jt{vnY(REQ~RU zF#4J>Mn~rX()BY;4-9fDn*`aCLxD8reAtsR=n_!1NVAC~5s hf>Ay&GEj}X)3`?A+g*S~hVw`fpFKL{13$U9{Xf9z3iJQ~ diff --git a/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java b/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java index e67620f..3b26960 100644 --- a/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java +++ b/src/main/java/cod/interpreter/handler/LoopOptimizationHandler.java @@ -22,6 +22,7 @@ public class LoopOptimizationHandler { private static final int LAZY_THRESHOLD = 10; private static final int MAX_SUPPORTED_LAG = 64; + private static final int MIN_VECTOR_SEQUENCES = 2; private static final int MAX_VECTOR_SEQUENCES = 64; private final InterpreterVisitor dispatcher; @@ -301,7 +302,7 @@ public List extractVectorLinearRecurrencePatterns( } List assignments = collectVectorAssignments(node); - if (assignments.size() < 2 || assignments.size() > MAX_VECTOR_SEQUENCES) { + if (assignments.size() < MIN_VECTOR_SEQUENCES || assignments.size() > MAX_VECTOR_SEQUENCES) { return results; } @@ -336,6 +337,7 @@ public List extractVectorLinearRecurrencePatterns( } int dimension = assignments.size(); + // coeffByLag[targetRow][lag][sourceColumn] AutoStackingNumber[][][] coeffByLag = new AutoStackingNumber[dimension][MAX_SUPPORTED_LAG + 1][dimension]; AutoStackingNumber[] constants = new AutoStackingNumber[dimension]; for (int row = 0; row < dimension; row++) { diff --git a/src/main/java/cod/range/formula/VectorRecurrenceFormula.java b/src/main/java/cod/range/formula/VectorRecurrenceFormula.java index 52e4b33..b91d9c2 100644 --- a/src/main/java/cod/range/formula/VectorRecurrenceFormula.java +++ b/src/main/java/cod/range/formula/VectorRecurrenceFormula.java @@ -49,7 +49,7 @@ public boolean contains(long index) { return index >= start && index <= end; } - public Object evaluate(long index, int sequenceIndex) { + public synchronized Object evaluate(long index, int sequenceIndex) { if (sequenceIndex < 0 || sequenceIndex >= dimension) { return null; } @@ -76,15 +76,13 @@ public Object evaluate(long index, int sequenceIndex) { return seedValues[sequenceIndex][seedOffset.intValue()]; } - synchronized (this) { - if (rollingState != null && index == rollingIndex) { - return rollingState[sequenceIndex]; - } - if (rollingState != null && index == rollingIndex + 1L) { - advanceRollingState(); - rollingIndex = index; - return rollingState[sequenceIndex]; - } + if (rollingState != null && index == rollingIndex) { + return rollingState[sequenceIndex]; + } + if (rollingState != null && index == rollingIndex + 1L) { + advanceRollingState(); + rollingIndex = index; + return rollingState[sequenceIndex]; } long lastSeedIndex = recurrenceStart - 1L; @@ -97,11 +95,9 @@ public Object evaluate(long index, int sequenceIndex) { AutoStackingNumber[][] power = matrixPow(transition, steps); AutoStackingNumber[] result = multiply(power, state); - synchronized (this) { - rollingState = Arrays.copyOf(result, baseDim); - rollingIndex = index; - return rollingState[sequenceIndex]; - } + rollingState = Arrays.copyOf(result, baseDim); + rollingIndex = index; + return rollingState[sequenceIndex]; } private AutoStackingNumber[][] buildTransition(int baseDim, int matrixDim) {