This is an automated email from the ASF dual-hosted git repository. robertlazarski pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/axis-axis2-java-core.git
commit 18fd259c55d6dd006178b6c98e79a7312160acc4 Author: Robert Lazarski <[email protected]> AuthorDate: Sun May 17 11:53:10 2026 -1000 AXIS2-5904 Fix same race condition in AxisMessage.isPolicyUpdated() AxisMessage has the identical Date.after() millisecond-granularity race as AxisBindingMessage (fixed in prior commit). Apply the same AtomicLong version counter fix. Both classes in the policy hierarchy that cache effective policies are now using monotonic counters. Co-Authored-By: Claude Opus 4.6 (1M context) <[email protected]> --- .../org/apache/axis2/description/AxisMessage.java | 40 ++++++++++++---------- 1 file changed, 22 insertions(+), 18 deletions(-) diff --git a/modules/kernel/src/org/apache/axis2/description/AxisMessage.java b/modules/kernel/src/org/apache/axis2/description/AxisMessage.java index f7a1d072a1..6f6fb88f65 100644 --- a/modules/kernel/src/org/apache/axis2/description/AxisMessage.java +++ b/modules/kernel/src/org/apache/axis2/description/AxisMessage.java @@ -68,6 +68,7 @@ public class AxisMessage extends AxisDescription { private volatile Policy effectivePolicy = null; private volatile Date lastPolicyCalculatedTime = null; + private volatile long lastPolicyCalculatedVersion = -1; public String getMessagePartName() { return messagePartName; @@ -237,11 +238,12 @@ public class AxisMessage extends AxisDescription { } public Policy getEffectivePolicy() { - if (lastPolicyCalculatedTime == null || isPolicyUpdated()) { + if (isPolicyUpdated()) { synchronized (this) { - if (lastPolicyCalculatedTime == null || isPolicyUpdated()) { + if (isPolicyUpdated()) { effectivePolicy = calculateEffectivePolicy(); lastPolicyCalculatedTime = new Date(); + lastPolicyCalculatedVersion = getMaxPolicyVersion(); } } } @@ -284,31 +286,33 @@ public class AxisMessage extends AxisDescription { } public boolean isPolicyUpdated() { - // AxisMessage - if (getPolicySubject().getLastUpdatedTime().after( - lastPolicyCalculatedTime)) { - return true; - } + return getMaxPolicyVersion() > lastPolicyCalculatedVersion; + } + + /** + * Returns the maximum policy version across the description hierarchy. + * Uses monotonic counter instead of Date to avoid the millisecond- + * granularity race condition in AXIS2-5904. + */ + private long getMaxPolicyVersion() { + long max = getPolicySubject().getVersion(); // AxisOperation AxisOperation axisOperation = (AxisOperation) parent; - if (axisOperation != null - && axisOperation.getPolicySubject().getLastUpdatedTime().after( - lastPolicyCalculatedTime)) { - return true; + if (axisOperation != null) { + max = Math.max(max, axisOperation.getPolicySubject().getVersion()); } // AxisService AxisService axisService = (axisOperation == null) ? null : axisOperation.getAxisService(); - if (axisService != null - && axisService.getPolicySubject().getLastUpdatedTime().after( - lastPolicyCalculatedTime)) { - return true; + if (axisService != null) { + max = Math.max(max, axisService.getPolicySubject().getVersion()); } // AxisConfiguration AxisConfiguration axisConfiguration = (axisService == null) ? null : axisService.getAxisConfiguration(); - return axisConfiguration != null - && axisConfiguration.getPolicySubject().getLastUpdatedTime() - .after(lastPolicyCalculatedTime); + if (axisConfiguration != null) { + max = Math.max(max, axisConfiguration.getPolicySubject().getVersion()); + } + return max; } }
